@tldraw/editor 3.14.0-canary.d15c939851b6 → 3.14.0-canary.d1b8a584b27c

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.
Files changed (56) hide show
  1. package/dist-cjs/index.d.ts +13 -96
  2. package/dist-cjs/index.js +1 -4
  3. package/dist-cjs/index.js.map +2 -2
  4. package/dist-cjs/lib/editor/Editor.js +24 -57
  5. package/dist-cjs/lib/editor/Editor.js.map +2 -2
  6. package/dist-cjs/lib/editor/managers/HistoryManager/HistoryManager.js +1 -3
  7. package/dist-cjs/lib/editor/managers/HistoryManager/HistoryManager.js.map +2 -2
  8. package/dist-cjs/lib/editor/shapes/ShapeUtil.js +10 -0
  9. package/dist-cjs/lib/editor/shapes/ShapeUtil.js.map +2 -2
  10. package/dist-cjs/lib/editor/tools/BaseBoxShapeTool/children/Pointing.js +6 -13
  11. package/dist-cjs/lib/editor/tools/BaseBoxShapeTool/children/Pointing.js.map +3 -3
  12. package/dist-cjs/lib/editor/types/emit-types.js.map +1 -1
  13. package/dist-cjs/lib/primitives/geometry/Geometry2d.js +2 -6
  14. package/dist-cjs/lib/primitives/geometry/Geometry2d.js.map +2 -2
  15. package/dist-cjs/lib/primitives/geometry/Group2d.js +6 -11
  16. package/dist-cjs/lib/primitives/geometry/Group2d.js.map +2 -2
  17. package/dist-cjs/lib/utils/dom.js +1 -1
  18. package/dist-cjs/lib/utils/dom.js.map +2 -2
  19. package/dist-cjs/version.js +3 -3
  20. package/dist-cjs/version.js.map +1 -1
  21. package/dist-esm/index.d.mts +13 -96
  22. package/dist-esm/index.mjs +1 -4
  23. package/dist-esm/index.mjs.map +2 -2
  24. package/dist-esm/lib/editor/Editor.mjs +24 -57
  25. package/dist-esm/lib/editor/Editor.mjs.map +2 -2
  26. package/dist-esm/lib/editor/managers/HistoryManager/HistoryManager.mjs +1 -3
  27. package/dist-esm/lib/editor/managers/HistoryManager/HistoryManager.mjs.map +2 -2
  28. package/dist-esm/lib/editor/shapes/ShapeUtil.mjs +10 -0
  29. package/dist-esm/lib/editor/shapes/ShapeUtil.mjs.map +2 -2
  30. package/dist-esm/lib/editor/tools/BaseBoxShapeTool/children/Pointing.mjs +6 -13
  31. package/dist-esm/lib/editor/tools/BaseBoxShapeTool/children/Pointing.mjs.map +3 -3
  32. package/dist-esm/lib/primitives/geometry/Geometry2d.mjs +2 -6
  33. package/dist-esm/lib/primitives/geometry/Geometry2d.mjs.map +2 -2
  34. package/dist-esm/lib/primitives/geometry/Group2d.mjs +6 -11
  35. package/dist-esm/lib/primitives/geometry/Group2d.mjs.map +2 -2
  36. package/dist-esm/lib/utils/dom.mjs +1 -1
  37. package/dist-esm/lib/utils/dom.mjs.map +2 -2
  38. package/dist-esm/version.mjs +3 -3
  39. package/dist-esm/version.mjs.map +1 -1
  40. package/editor.css +11 -17
  41. package/package.json +7 -7
  42. package/src/index.ts +0 -5
  43. package/src/lib/editor/Editor.ts +35 -75
  44. package/src/lib/editor/managers/HistoryManager/HistoryManager.ts +1 -3
  45. package/src/lib/editor/shapes/ShapeUtil.ts +15 -46
  46. package/src/lib/editor/tools/BaseBoxShapeTool/children/Pointing.ts +17 -25
  47. package/src/lib/editor/types/emit-types.ts +0 -4
  48. package/src/lib/primitives/geometry/Geometry2d.ts +2 -7
  49. package/src/lib/primitives/geometry/Group2d.ts +5 -11
  50. package/src/lib/utils/dom.ts +1 -1
  51. package/src/version.ts +3 -3
  52. package/dist-cjs/lib/utils/reparenting.js +0 -232
  53. package/dist-cjs/lib/utils/reparenting.js.map +0 -7
  54. package/dist-esm/lib/utils/reparenting.mjs +0 -216
  55. package/dist-esm/lib/utils/reparenting.mjs.map +0 -7
  56. package/src/lib/utils/reparenting.ts +0 -383
@@ -209,9 +209,7 @@ class HistoryManager {
209
209
  return this;
210
210
  }
211
211
  bailToMark(id) {
212
- if (id) {
213
- this._undo({ pushToRedoStack: false, toMark: id });
214
- }
212
+ this._undo({ pushToRedoStack: false, toMark: id });
215
213
  return this;
216
214
  }
217
215
  squashToMark(id) {
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../../src/lib/editor/managers/HistoryManager/HistoryManager.ts"],
4
- "sourcesContent": ["import { atom, transact } from '@tldraw/state'\nimport {\n\tRecordsDiff,\n\tStore,\n\tUnknownRecord,\n\tcreateEmptyRecordsDiff,\n\tisRecordsDiffEmpty,\n\treverseRecordsDiff,\n\tsquashRecordDiffsMutable,\n} from '@tldraw/store'\nimport { exhaustiveSwitchError, noop } from '@tldraw/utils'\nimport { TLHistoryBatchOptions, TLHistoryEntry } from '../../types/history-types'\n\nenum HistoryRecorderState {\n\tRecording = 'recording',\n\tRecordingPreserveRedoStack = 'recordingPreserveRedoStack',\n\tPaused = 'paused',\n}\n\n/** @public */\nexport class HistoryManager<R extends UnknownRecord> {\n\tprivate readonly store: Store<R>\n\n\treadonly dispose: () => void\n\n\tprivate state: HistoryRecorderState = HistoryRecorderState.Recording\n\tprivate readonly pendingDiff = new PendingDiff<R>()\n\tprivate stacks = atom(\n\t\t'HistoryManager.stacks',\n\t\t{\n\t\t\tundos: stack<TLHistoryEntry<R>>(),\n\t\t\tredos: stack<TLHistoryEntry<R>>(),\n\t\t},\n\t\t{\n\t\t\tisEqual: (a, b) => a.undos === b.undos && a.redos === b.redos,\n\t\t}\n\t)\n\n\tprivate readonly annotateError: (error: unknown) => void\n\n\tconstructor(opts: { store: Store<R>; annotateError?(error: unknown): void }) {\n\t\tthis.store = opts.store\n\t\tthis.annotateError = opts.annotateError ?? noop\n\t\tthis.dispose = this.store.addHistoryInterceptor((entry, source) => {\n\t\t\tif (source !== 'user') return\n\n\t\t\tswitch (this.state) {\n\t\t\t\tcase HistoryRecorderState.Recording:\n\t\t\t\t\tthis.pendingDiff.apply(entry.changes)\n\t\t\t\t\tthis.stacks.update(({ undos }) => ({ undos, redos: stack() }))\n\t\t\t\t\tbreak\n\t\t\t\tcase HistoryRecorderState.RecordingPreserveRedoStack:\n\t\t\t\t\tthis.pendingDiff.apply(entry.changes)\n\t\t\t\t\tbreak\n\t\t\t\tcase HistoryRecorderState.Paused:\n\t\t\t\t\tbreak\n\t\t\t\tdefault:\n\t\t\t\t\texhaustiveSwitchError(this.state)\n\t\t\t}\n\t\t})\n\t}\n\n\tprivate flushPendingDiff() {\n\t\tif (this.pendingDiff.isEmpty()) return\n\n\t\tconst diff = this.pendingDiff.clear()\n\t\tthis.stacks.update(({ undos, redos }) => ({\n\t\t\tundos: undos.push({ type: 'diff', diff }),\n\t\t\tredos,\n\t\t}))\n\t}\n\n\tgetNumUndos() {\n\t\treturn this.stacks.get().undos.length + (this.pendingDiff.isEmpty() ? 0 : 1)\n\t}\n\n\tgetNumRedos() {\n\t\treturn this.stacks.get().redos.length\n\t}\n\n\t/** @internal */\n\t_isInBatch = false\n\n\tbatch(fn: () => void, opts?: TLHistoryBatchOptions) {\n\t\tconst previousState = this.state\n\n\t\t// we move to the new state only if we haven't explicitly paused\n\t\tif (previousState !== HistoryRecorderState.Paused && opts?.history) {\n\t\t\tthis.state = modeToState[opts.history]\n\t\t}\n\n\t\ttry {\n\t\t\tif (this._isInBatch) {\n\t\t\t\ttransact(fn)\n\t\t\t\treturn this\n\t\t\t}\n\n\t\t\tthis._isInBatch = true\n\t\t\ttry {\n\t\t\t\ttransact(fn)\n\t\t\t} catch (error) {\n\t\t\t\tthis.annotateError(error)\n\t\t\t\tthrow error\n\t\t\t} finally {\n\t\t\t\tthis._isInBatch = false\n\t\t\t}\n\n\t\t\treturn this\n\t\t} finally {\n\t\t\tthis.state = previousState\n\t\t}\n\t}\n\n\t// History\n\t_undo({ pushToRedoStack, toMark = undefined }: { pushToRedoStack: boolean; toMark?: string }) {\n\t\tconst previousState = this.state\n\t\tthis.state = HistoryRecorderState.Paused\n\t\ttry {\n\t\t\tlet { undos, redos } = this.stacks.get()\n\n\t\t\t// start by collecting the pending diff (everything since the last mark).\n\t\t\t// we'll accumulate the diff to undo in this variable so we can apply it atomically.\n\t\t\tconst pendingDiff = this.pendingDiff.clear()\n\t\t\tconst isPendingDiffEmpty = isRecordsDiffEmpty(pendingDiff)\n\t\t\tconst diffToUndo = reverseRecordsDiff(pendingDiff)\n\n\t\t\tif (pushToRedoStack && !isPendingDiffEmpty) {\n\t\t\t\tredos = redos.push({ type: 'diff', diff: pendingDiff })\n\t\t\t}\n\n\t\t\tlet didFindMark = false\n\t\t\tif (isPendingDiffEmpty) {\n\t\t\t\t// if nothing has happened since the last mark, pop any intermediate marks off the stack\n\t\t\t\twhile (undos.head?.type === 'stop') {\n\t\t\t\t\tconst mark = undos.head\n\t\t\t\t\tundos = undos.tail\n\t\t\t\t\tif (pushToRedoStack) {\n\t\t\t\t\t\tredos = redos.push(mark)\n\t\t\t\t\t}\n\t\t\t\t\tif (mark.id === toMark) {\n\t\t\t\t\t\tdidFindMark = true\n\t\t\t\t\t\tbreak\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (!didFindMark) {\n\t\t\t\tloop: while (undos.head) {\n\t\t\t\t\tconst undo = undos.head\n\t\t\t\t\tundos = undos.tail\n\n\t\t\t\t\tif (pushToRedoStack) {\n\t\t\t\t\t\tredos = redos.push(undo)\n\t\t\t\t\t}\n\n\t\t\t\t\tswitch (undo.type) {\n\t\t\t\t\t\tcase 'diff':\n\t\t\t\t\t\t\tsquashRecordDiffsMutable(diffToUndo, [reverseRecordsDiff(undo.diff)])\n\t\t\t\t\t\t\tbreak\n\t\t\t\t\t\tcase 'stop':\n\t\t\t\t\t\t\tif (!toMark) break loop\n\t\t\t\t\t\t\tif (undo.id === toMark) {\n\t\t\t\t\t\t\t\tdidFindMark = true\n\t\t\t\t\t\t\t\tbreak loop\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tbreak\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\texhaustiveSwitchError(undo)\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (!didFindMark && toMark) {\n\t\t\t\t// whoops, we didn't find the mark we were looking for\n\t\t\t\t// don't do anything\n\t\t\t\treturn this\n\t\t\t}\n\n\t\t\tthis.store.applyDiff(diffToUndo, { ignoreEphemeralKeys: true })\n\t\t\tthis.store.ensureStoreIsUsable()\n\t\t\tthis.stacks.set({ undos, redos })\n\t\t} finally {\n\t\t\tthis.state = previousState\n\t\t}\n\n\t\treturn this\n\t}\n\n\tundo() {\n\t\tthis._undo({ pushToRedoStack: true })\n\n\t\treturn this\n\t}\n\n\tredo() {\n\t\tconst previousState = this.state\n\t\tthis.state = HistoryRecorderState.Paused\n\t\ttry {\n\t\t\tthis.flushPendingDiff()\n\n\t\t\tlet { undos, redos } = this.stacks.get()\n\t\t\tif (redos.length === 0) {\n\t\t\t\treturn this\n\t\t\t}\n\n\t\t\t// ignore any intermediate marks - this should take us to the first `diff` entry\n\t\t\twhile (redos.head?.type === 'stop') {\n\t\t\t\tundos = undos.push(redos.head)\n\t\t\t\tredos = redos.tail\n\t\t\t}\n\n\t\t\t// accumulate diffs to be redone so they can be applied atomically\n\t\t\tconst diffToRedo = createEmptyRecordsDiff<R>()\n\n\t\t\twhile (redos.head) {\n\t\t\t\tconst redo = redos.head\n\t\t\t\tundos = undos.push(redo)\n\t\t\t\tredos = redos.tail\n\n\t\t\t\tif (redo.type === 'diff') {\n\t\t\t\t\tsquashRecordDiffsMutable(diffToRedo, [redo.diff])\n\t\t\t\t} else {\n\t\t\t\t\tbreak\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tthis.store.applyDiff(diffToRedo, { ignoreEphemeralKeys: true })\n\t\t\tthis.store.ensureStoreIsUsable()\n\t\t\tthis.stacks.set({ undos, redos })\n\t\t} finally {\n\t\t\tthis.state = previousState\n\t\t}\n\n\t\treturn this\n\t}\n\n\tbail() {\n\t\tthis._undo({ pushToRedoStack: false })\n\n\t\treturn this\n\t}\n\n\tbailToMark(id: string) {\n\t\tif (id) {\n\t\t\tthis._undo({ pushToRedoStack: false, toMark: id })\n\t\t}\n\n\t\treturn this\n\t}\n\n\tsquashToMark(id: string) {\n\t\t// remove marks between head and the mark\n\n\t\tlet top = this.stacks.get().undos\n\t\tconst popped: Array<RecordsDiff<R>> = []\n\n\t\twhile (top.head && !(top.head.type === 'stop' && top.head.id === id)) {\n\t\t\tif (top.head.type === 'diff') {\n\t\t\t\tpopped.push(top.head.diff)\n\t\t\t}\n\t\t\ttop = top.tail\n\t\t}\n\n\t\tif (!top.head || top.head?.id !== id) {\n\t\t\tconsole.error('Could not find mark to squash to: ', id)\n\t\t\treturn this\n\t\t}\n\t\tif (popped.length === 0) {\n\t\t\treturn this\n\t\t}\n\n\t\tconst diff = createEmptyRecordsDiff<R>()\n\t\tsquashRecordDiffsMutable(diff, popped.reverse())\n\n\t\tthis.stacks.update(({ redos }) => ({\n\t\t\tundos: top.push({\n\t\t\t\ttype: 'diff',\n\t\t\t\tdiff,\n\t\t\t}),\n\t\t\tredos,\n\t\t}))\n\n\t\treturn this\n\t}\n\n\t/** @internal */\n\t_mark(id: string) {\n\t\ttransact(() => {\n\t\t\tthis.flushPendingDiff()\n\t\t\tthis.stacks.update(({ undos, redos }) => ({ undos: undos.push({ type: 'stop', id }), redos }))\n\t\t})\n\t}\n\n\tclear() {\n\t\tthis.stacks.set({ undos: stack(), redos: stack() })\n\t\tthis.pendingDiff.clear()\n\t}\n\n\t/** @internal */\n\tgetMarkIdMatching(idSubstring: string) {\n\t\tlet top = this.stacks.get().undos\n\t\twhile (top.head) {\n\t\t\tif (top.head.type === 'stop' && top.head.id.includes(idSubstring)) {\n\t\t\t\treturn top.head.id\n\t\t\t}\n\t\t\ttop = top.tail\n\t\t}\n\t\treturn null\n\t}\n\n\t/** @internal */\n\tdebug() {\n\t\tconst { undos, redos } = this.stacks.get()\n\t\treturn {\n\t\t\tundos: undos.toArray(),\n\t\t\tredos: redos.toArray(),\n\t\t\tpendingDiff: this.pendingDiff.debug(),\n\t\t\tstate: this.state as string,\n\t\t}\n\t}\n}\n\nconst modeToState = {\n\trecord: HistoryRecorderState.Recording,\n\t'record-preserveRedoStack': HistoryRecorderState.RecordingPreserveRedoStack,\n\tignore: HistoryRecorderState.Paused,\n} as const\n\nclass PendingDiff<R extends UnknownRecord> {\n\tprivate diff = createEmptyRecordsDiff<R>()\n\tprivate isEmptyAtom = atom('PendingDiff.isEmpty', true)\n\n\tclear() {\n\t\tconst diff = this.diff\n\t\tthis.diff = createEmptyRecordsDiff<R>()\n\t\tthis.isEmptyAtom.set(true)\n\t\treturn diff\n\t}\n\n\tisEmpty() {\n\t\treturn this.isEmptyAtom.get()\n\t}\n\n\tapply(diff: RecordsDiff<R>) {\n\t\tsquashRecordDiffsMutable(this.diff, [diff])\n\t\tthis.isEmptyAtom.set(isRecordsDiffEmpty(this.diff))\n\t}\n\n\tdebug() {\n\t\treturn { diff: this.diff, isEmpty: this.isEmpty() }\n\t}\n}\n\nimport { EMPTY_ARRAY } from '@tldraw/state'\n\nexport type Stack<T> = StackItem<T> | EmptyStackItem<T>\n\nexport function stack<T>(items?: Array<T>): Stack<T> {\n\tif (items) {\n\t\tlet result = EMPTY_STACK_ITEM as Stack<T>\n\t\twhile (items.length) {\n\t\t\tresult = result.push(items.pop()!)\n\t\t}\n\t\treturn result\n\t}\n\treturn EMPTY_STACK_ITEM as any\n}\n\nclass EmptyStackItem<T> implements Iterable<T> {\n\treadonly length = 0\n\treadonly head = null\n\treadonly tail: Stack<T> = this\n\n\tpush(head: T): Stack<T> {\n\t\treturn new StackItem<T>(head, this)\n\t}\n\n\ttoArray() {\n\t\treturn EMPTY_ARRAY\n\t}\n\n\t[Symbol.iterator]() {\n\t\treturn {\n\t\t\tnext() {\n\t\t\t\treturn { value: undefined, done: true as const }\n\t\t\t},\n\t\t}\n\t}\n}\n\nconst EMPTY_STACK_ITEM = new EmptyStackItem()\n\nclass StackItem<T> implements Iterable<T> {\n\tlength: number\n\tconstructor(\n\t\tpublic readonly head: T,\n\t\tpublic readonly tail: Stack<T>\n\t) {\n\t\tthis.length = tail.length + 1\n\t}\n\n\tpush(head: T): Stack<T> {\n\t\treturn new StackItem(head, this)\n\t}\n\n\ttoArray() {\n\t\treturn Array.from(this)\n\t}\n\n\t[Symbol.iterator]() {\n\t\tlet stack = this as Stack<T>\n\t\treturn {\n\t\t\tnext() {\n\t\t\t\tif (stack.length) {\n\t\t\t\t\tconst value = stack.head!\n\t\t\t\t\tstack = stack.tail\n\t\t\t\t\treturn { value, done: false as const }\n\t\t\t\t} else {\n\t\t\t\t\treturn { value: undefined, done: true as const }\n\t\t\t\t}\n\t\t\t},\n\t\t}\n\t}\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import { atom, transact } from '@tldraw/state'\nimport {\n\tRecordsDiff,\n\tStore,\n\tUnknownRecord,\n\tcreateEmptyRecordsDiff,\n\tisRecordsDiffEmpty,\n\treverseRecordsDiff,\n\tsquashRecordDiffsMutable,\n} from '@tldraw/store'\nimport { exhaustiveSwitchError, noop } from '@tldraw/utils'\nimport { TLHistoryBatchOptions, TLHistoryEntry } from '../../types/history-types'\n\nenum HistoryRecorderState {\n\tRecording = 'recording',\n\tRecordingPreserveRedoStack = 'recordingPreserveRedoStack',\n\tPaused = 'paused',\n}\n\n/** @public */\nexport class HistoryManager<R extends UnknownRecord> {\n\tprivate readonly store: Store<R>\n\n\treadonly dispose: () => void\n\n\tprivate state: HistoryRecorderState = HistoryRecorderState.Recording\n\tprivate readonly pendingDiff = new PendingDiff<R>()\n\tprivate stacks = atom(\n\t\t'HistoryManager.stacks',\n\t\t{\n\t\t\tundos: stack<TLHistoryEntry<R>>(),\n\t\t\tredos: stack<TLHistoryEntry<R>>(),\n\t\t},\n\t\t{\n\t\t\tisEqual: (a, b) => a.undos === b.undos && a.redos === b.redos,\n\t\t}\n\t)\n\n\tprivate readonly annotateError: (error: unknown) => void\n\n\tconstructor(opts: { store: Store<R>; annotateError?(error: unknown): void }) {\n\t\tthis.store = opts.store\n\t\tthis.annotateError = opts.annotateError ?? noop\n\t\tthis.dispose = this.store.addHistoryInterceptor((entry, source) => {\n\t\t\tif (source !== 'user') return\n\n\t\t\tswitch (this.state) {\n\t\t\t\tcase HistoryRecorderState.Recording:\n\t\t\t\t\tthis.pendingDiff.apply(entry.changes)\n\t\t\t\t\tthis.stacks.update(({ undos }) => ({ undos, redos: stack() }))\n\t\t\t\t\tbreak\n\t\t\t\tcase HistoryRecorderState.RecordingPreserveRedoStack:\n\t\t\t\t\tthis.pendingDiff.apply(entry.changes)\n\t\t\t\t\tbreak\n\t\t\t\tcase HistoryRecorderState.Paused:\n\t\t\t\t\tbreak\n\t\t\t\tdefault:\n\t\t\t\t\texhaustiveSwitchError(this.state)\n\t\t\t}\n\t\t})\n\t}\n\n\tprivate flushPendingDiff() {\n\t\tif (this.pendingDiff.isEmpty()) return\n\n\t\tconst diff = this.pendingDiff.clear()\n\t\tthis.stacks.update(({ undos, redos }) => ({\n\t\t\tundos: undos.push({ type: 'diff', diff }),\n\t\t\tredos,\n\t\t}))\n\t}\n\n\tgetNumUndos() {\n\t\treturn this.stacks.get().undos.length + (this.pendingDiff.isEmpty() ? 0 : 1)\n\t}\n\n\tgetNumRedos() {\n\t\treturn this.stacks.get().redos.length\n\t}\n\n\t/** @internal */\n\t_isInBatch = false\n\n\tbatch(fn: () => void, opts?: TLHistoryBatchOptions) {\n\t\tconst previousState = this.state\n\n\t\t// we move to the new state only if we haven't explicitly paused\n\t\tif (previousState !== HistoryRecorderState.Paused && opts?.history) {\n\t\t\tthis.state = modeToState[opts.history]\n\t\t}\n\n\t\ttry {\n\t\t\tif (this._isInBatch) {\n\t\t\t\ttransact(fn)\n\t\t\t\treturn this\n\t\t\t}\n\n\t\t\tthis._isInBatch = true\n\t\t\ttry {\n\t\t\t\ttransact(fn)\n\t\t\t} catch (error) {\n\t\t\t\tthis.annotateError(error)\n\t\t\t\tthrow error\n\t\t\t} finally {\n\t\t\t\tthis._isInBatch = false\n\t\t\t}\n\n\t\t\treturn this\n\t\t} finally {\n\t\t\tthis.state = previousState\n\t\t}\n\t}\n\n\t// History\n\t_undo({ pushToRedoStack, toMark = undefined }: { pushToRedoStack: boolean; toMark?: string }) {\n\t\tconst previousState = this.state\n\t\tthis.state = HistoryRecorderState.Paused\n\t\ttry {\n\t\t\tlet { undos, redos } = this.stacks.get()\n\n\t\t\t// start by collecting the pending diff (everything since the last mark).\n\t\t\t// we'll accumulate the diff to undo in this variable so we can apply it atomically.\n\t\t\tconst pendingDiff = this.pendingDiff.clear()\n\t\t\tconst isPendingDiffEmpty = isRecordsDiffEmpty(pendingDiff)\n\t\t\tconst diffToUndo = reverseRecordsDiff(pendingDiff)\n\n\t\t\tif (pushToRedoStack && !isPendingDiffEmpty) {\n\t\t\t\tredos = redos.push({ type: 'diff', diff: pendingDiff })\n\t\t\t}\n\n\t\t\tlet didFindMark = false\n\t\t\tif (isPendingDiffEmpty) {\n\t\t\t\t// if nothing has happened since the last mark, pop any intermediate marks off the stack\n\t\t\t\twhile (undos.head?.type === 'stop') {\n\t\t\t\t\tconst mark = undos.head\n\t\t\t\t\tundos = undos.tail\n\t\t\t\t\tif (pushToRedoStack) {\n\t\t\t\t\t\tredos = redos.push(mark)\n\t\t\t\t\t}\n\t\t\t\t\tif (mark.id === toMark) {\n\t\t\t\t\t\tdidFindMark = true\n\t\t\t\t\t\tbreak\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (!didFindMark) {\n\t\t\t\tloop: while (undos.head) {\n\t\t\t\t\tconst undo = undos.head\n\t\t\t\t\tundos = undos.tail\n\n\t\t\t\t\tif (pushToRedoStack) {\n\t\t\t\t\t\tredos = redos.push(undo)\n\t\t\t\t\t}\n\n\t\t\t\t\tswitch (undo.type) {\n\t\t\t\t\t\tcase 'diff':\n\t\t\t\t\t\t\tsquashRecordDiffsMutable(diffToUndo, [reverseRecordsDiff(undo.diff)])\n\t\t\t\t\t\t\tbreak\n\t\t\t\t\t\tcase 'stop':\n\t\t\t\t\t\t\tif (!toMark) break loop\n\t\t\t\t\t\t\tif (undo.id === toMark) {\n\t\t\t\t\t\t\t\tdidFindMark = true\n\t\t\t\t\t\t\t\tbreak loop\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tbreak\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\texhaustiveSwitchError(undo)\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (!didFindMark && toMark) {\n\t\t\t\t// whoops, we didn't find the mark we were looking for\n\t\t\t\t// don't do anything\n\t\t\t\treturn this\n\t\t\t}\n\n\t\t\tthis.store.applyDiff(diffToUndo, { ignoreEphemeralKeys: true })\n\t\t\tthis.store.ensureStoreIsUsable()\n\t\t\tthis.stacks.set({ undos, redos })\n\t\t} finally {\n\t\t\tthis.state = previousState\n\t\t}\n\n\t\treturn this\n\t}\n\n\tundo() {\n\t\tthis._undo({ pushToRedoStack: true })\n\n\t\treturn this\n\t}\n\n\tredo() {\n\t\tconst previousState = this.state\n\t\tthis.state = HistoryRecorderState.Paused\n\t\ttry {\n\t\t\tthis.flushPendingDiff()\n\n\t\t\tlet { undos, redos } = this.stacks.get()\n\t\t\tif (redos.length === 0) {\n\t\t\t\treturn this\n\t\t\t}\n\n\t\t\t// ignore any intermediate marks - this should take us to the first `diff` entry\n\t\t\twhile (redos.head?.type === 'stop') {\n\t\t\t\tundos = undos.push(redos.head)\n\t\t\t\tredos = redos.tail\n\t\t\t}\n\n\t\t\t// accumulate diffs to be redone so they can be applied atomically\n\t\t\tconst diffToRedo = createEmptyRecordsDiff<R>()\n\n\t\t\twhile (redos.head) {\n\t\t\t\tconst redo = redos.head\n\t\t\t\tundos = undos.push(redo)\n\t\t\t\tredos = redos.tail\n\n\t\t\t\tif (redo.type === 'diff') {\n\t\t\t\t\tsquashRecordDiffsMutable(diffToRedo, [redo.diff])\n\t\t\t\t} else {\n\t\t\t\t\tbreak\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tthis.store.applyDiff(diffToRedo, { ignoreEphemeralKeys: true })\n\t\t\tthis.store.ensureStoreIsUsable()\n\t\t\tthis.stacks.set({ undos, redos })\n\t\t} finally {\n\t\t\tthis.state = previousState\n\t\t}\n\n\t\treturn this\n\t}\n\n\tbail() {\n\t\tthis._undo({ pushToRedoStack: false })\n\n\t\treturn this\n\t}\n\n\tbailToMark(id: string) {\n\t\tthis._undo({ pushToRedoStack: false, toMark: id })\n\n\t\treturn this\n\t}\n\n\tsquashToMark(id: string) {\n\t\t// remove marks between head and the mark\n\n\t\tlet top = this.stacks.get().undos\n\t\tconst popped: Array<RecordsDiff<R>> = []\n\n\t\twhile (top.head && !(top.head.type === 'stop' && top.head.id === id)) {\n\t\t\tif (top.head.type === 'diff') {\n\t\t\t\tpopped.push(top.head.diff)\n\t\t\t}\n\t\t\ttop = top.tail\n\t\t}\n\n\t\tif (!top.head || top.head?.id !== id) {\n\t\t\tconsole.error('Could not find mark to squash to: ', id)\n\t\t\treturn this\n\t\t}\n\t\tif (popped.length === 0) {\n\t\t\treturn this\n\t\t}\n\n\t\tconst diff = createEmptyRecordsDiff<R>()\n\t\tsquashRecordDiffsMutable(diff, popped.reverse())\n\n\t\tthis.stacks.update(({ redos }) => ({\n\t\t\tundos: top.push({\n\t\t\t\ttype: 'diff',\n\t\t\t\tdiff,\n\t\t\t}),\n\t\t\tredos,\n\t\t}))\n\n\t\treturn this\n\t}\n\n\t/** @internal */\n\t_mark(id: string) {\n\t\ttransact(() => {\n\t\t\tthis.flushPendingDiff()\n\t\t\tthis.stacks.update(({ undos, redos }) => ({ undos: undos.push({ type: 'stop', id }), redos }))\n\t\t})\n\t}\n\n\tclear() {\n\t\tthis.stacks.set({ undos: stack(), redos: stack() })\n\t\tthis.pendingDiff.clear()\n\t}\n\n\t/** @internal */\n\tgetMarkIdMatching(idSubstring: string) {\n\t\tlet top = this.stacks.get().undos\n\t\twhile (top.head) {\n\t\t\tif (top.head.type === 'stop' && top.head.id.includes(idSubstring)) {\n\t\t\t\treturn top.head.id\n\t\t\t}\n\t\t\ttop = top.tail\n\t\t}\n\t\treturn null\n\t}\n\n\t/** @internal */\n\tdebug() {\n\t\tconst { undos, redos } = this.stacks.get()\n\t\treturn {\n\t\t\tundos: undos.toArray(),\n\t\t\tredos: redos.toArray(),\n\t\t\tpendingDiff: this.pendingDiff.debug(),\n\t\t\tstate: this.state as string,\n\t\t}\n\t}\n}\n\nconst modeToState = {\n\trecord: HistoryRecorderState.Recording,\n\t'record-preserveRedoStack': HistoryRecorderState.RecordingPreserveRedoStack,\n\tignore: HistoryRecorderState.Paused,\n} as const\n\nclass PendingDiff<R extends UnknownRecord> {\n\tprivate diff = createEmptyRecordsDiff<R>()\n\tprivate isEmptyAtom = atom('PendingDiff.isEmpty', true)\n\n\tclear() {\n\t\tconst diff = this.diff\n\t\tthis.diff = createEmptyRecordsDiff<R>()\n\t\tthis.isEmptyAtom.set(true)\n\t\treturn diff\n\t}\n\n\tisEmpty() {\n\t\treturn this.isEmptyAtom.get()\n\t}\n\n\tapply(diff: RecordsDiff<R>) {\n\t\tsquashRecordDiffsMutable(this.diff, [diff])\n\t\tthis.isEmptyAtom.set(isRecordsDiffEmpty(this.diff))\n\t}\n\n\tdebug() {\n\t\treturn { diff: this.diff, isEmpty: this.isEmpty() }\n\t}\n}\n\nimport { EMPTY_ARRAY } from '@tldraw/state'\n\nexport type Stack<T> = StackItem<T> | EmptyStackItem<T>\n\nexport function stack<T>(items?: Array<T>): Stack<T> {\n\tif (items) {\n\t\tlet result = EMPTY_STACK_ITEM as Stack<T>\n\t\twhile (items.length) {\n\t\t\tresult = result.push(items.pop()!)\n\t\t}\n\t\treturn result\n\t}\n\treturn EMPTY_STACK_ITEM as any\n}\n\nclass EmptyStackItem<T> implements Iterable<T> {\n\treadonly length = 0\n\treadonly head = null\n\treadonly tail: Stack<T> = this\n\n\tpush(head: T): Stack<T> {\n\t\treturn new StackItem<T>(head, this)\n\t}\n\n\ttoArray() {\n\t\treturn EMPTY_ARRAY\n\t}\n\n\t[Symbol.iterator]() {\n\t\treturn {\n\t\t\tnext() {\n\t\t\t\treturn { value: undefined, done: true as const }\n\t\t\t},\n\t\t}\n\t}\n}\n\nconst EMPTY_STACK_ITEM = new EmptyStackItem()\n\nclass StackItem<T> implements Iterable<T> {\n\tlength: number\n\tconstructor(\n\t\tpublic readonly head: T,\n\t\tpublic readonly tail: Stack<T>\n\t) {\n\t\tthis.length = tail.length + 1\n\t}\n\n\tpush(head: T): Stack<T> {\n\t\treturn new StackItem(head, this)\n\t}\n\n\ttoArray() {\n\t\treturn Array.from(this)\n\t}\n\n\t[Symbol.iterator]() {\n\t\tlet stack = this as Stack<T>\n\t\treturn {\n\t\t\tnext() {\n\t\t\t\tif (stack.length) {\n\t\t\t\t\tconst value = stack.head!\n\t\t\t\t\tstack = stack.tail\n\t\t\t\t\treturn { value, done: false as const }\n\t\t\t\t} else {\n\t\t\t\t\treturn { value: undefined, done: true as const }\n\t\t\t\t}\n\t\t\t},\n\t\t}\n\t}\n}\n"],
5
+ "mappings": "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",
6
6
  "names": ["import_state", "HistoryRecorderState", "stack"]
7
7
  }
@@ -237,6 +237,16 @@ class ShapeUtil {
237
237
  canReceiveNewChildrenOfType(_shape, _type) {
238
238
  return false;
239
239
  }
240
+ /**
241
+ * Get whether the shape can receive children of a given type.
242
+ *
243
+ * @param shape - The shape type.
244
+ * @param shapes - The shapes that are being dropped.
245
+ * @public
246
+ */
247
+ canDropShapes(_shape, _shapes) {
248
+ return false;
249
+ }
240
250
  /** @internal */
241
251
  expandSelectionOutlinePx(shape) {
242
252
  return 0;
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../src/lib/editor/shapes/ShapeUtil.ts"],
4
- "sourcesContent": ["/* eslint-disable @typescript-eslint/no-unused-vars */\nimport { EMPTY_ARRAY } from '@tldraw/state'\nimport { LegacyMigrations, MigrationSequence } from '@tldraw/store'\nimport {\n\tRecordProps,\n\tTLHandle,\n\tTLParentId,\n\tTLPropsMigrations,\n\tTLShape,\n\tTLShapeCrop,\n\tTLShapeId,\n\tTLShapePartial,\n\tTLUnknownShape,\n} from '@tldraw/tlschema'\nimport { IndexKey } from '@tldraw/utils'\nimport { ReactElement } from 'react'\nimport { Box, SelectionHandle } from '../../primitives/Box'\nimport { Vec } from '../../primitives/Vec'\nimport { Geometry2d } from '../../primitives/geometry/Geometry2d'\nimport type { Editor } from '../Editor'\nimport { TLFontFace } from '../managers/FontManager/FontManager'\nimport { BoundsSnapGeometry } from '../managers/SnapManager/BoundsSnaps'\nimport { HandleSnapGeometry } from '../managers/SnapManager/HandleSnaps'\nimport { SvgExportContext } from '../types/SvgExportContext'\nimport { TLClickEventInfo } from '../types/event-types'\nimport { TLResizeHandle } from '../types/selection-types'\n\n/** @public */\nexport interface TLShapeUtilConstructor<\n\tT extends TLUnknownShape,\n\tU extends ShapeUtil<T> = ShapeUtil<T>,\n> {\n\tnew (editor: Editor): U\n\ttype: T['type']\n\tprops?: RecordProps<T>\n\tmigrations?: LegacyMigrations | TLPropsMigrations | MigrationSequence\n}\n\n/**\n * Options passed to {@link ShapeUtil.canBind}. A binding that could be made. At least one of\n * `fromShapeType` or `toShapeType` will belong to this shape util.\n *\n * @public\n */\nexport interface TLShapeUtilCanBindOpts<Shape extends TLUnknownShape = TLUnknownShape> {\n\t/** The type of shape referenced by the `fromId` of the binding. */\n\tfromShapeType: string\n\t/** The type of shape referenced by the `toId` of the binding. */\n\ttoShapeType: string\n\t/** The type of binding. */\n\tbindingType: string\n}\n\n/**\n * Options passed to {@link ShapeUtil.canBeLaidOut}.\n *\n * @public\n */\nexport interface TLShapeUtilCanBeLaidOutOpts {\n\t/** The type of action causing the layout. */\n\ttype?: 'align' | 'distribute' | 'pack' | 'stack' | 'flip' | 'stretch'\n\t/** The other shapes being laid out */\n\tshapes?: TLShape[]\n}\n\n/** Additional options for the {@link ShapeUtil.getGeometry} method.\n *\n * @public\n */\nexport interface TLGeometryOpts {\n\t/** The context in which the geometry is being requested. */\n\tcontext?: string\n}\n\n/** @public */\nexport interface TLShapeUtilCanvasSvgDef {\n\tkey: string\n\tcomponent: React.ComponentType\n}\n\n/** @public */\nexport abstract class ShapeUtil<Shape extends TLUnknownShape = TLUnknownShape> {\n\t/** Configure this shape utils {@link ShapeUtil.options | `options`}. */\n\tstatic configure<T extends TLShapeUtilConstructor<any, any>>(\n\t\tthis: T,\n\t\toptions: T extends new (...args: any[]) => { options: infer Options } ? Partial<Options> : never\n\t): T {\n\t\t// @ts-expect-error -- typescript has no idea what's going on here but it's fine\n\t\treturn class extends this {\n\t\t\t// @ts-expect-error\n\t\t\toptions = { ...this.options, ...options }\n\t\t}\n\t}\n\n\tconstructor(public editor: Editor) {}\n\n\t/**\n\t * Options for this shape util. If you're implementing a custom shape util, you can override\n\t * this to provide customization options for your shape. If using an existing shape util, you\n\t * can customizing this by calling {@link ShapeUtil.configure}.\n\t */\n\toptions = {}\n\n\t/**\n\t * Props allow you to define the shape's properties in a way that the editor can understand.\n\t * This has two main uses:\n\t *\n\t * 1. Validation. Shapes will be validated using these props to stop bad data from being saved.\n\t * 2. Styles. Each {@link @tldraw/tlschema#StyleProp} in the props can be set on many shapes at\n\t * once, and will be remembered from one shape to the next.\n\t *\n\t * @example\n\t * ```tsx\n\t * import {T, TLBaseShape, TLDefaultColorStyle, DefaultColorStyle, ShapeUtil} from 'tldraw'\n\t *\n\t * type MyShape = TLBaseShape<'mine', {\n\t * color: TLDefaultColorStyle,\n\t * text: string,\n\t * }>\n\t *\n\t * class MyShapeUtil extends ShapeUtil<MyShape> {\n\t * static props = {\n\t * // we use tldraw's built-in color style:\n\t * color: DefaultColorStyle,\n\t * // validate that the text prop is a string:\n\t * text: T.string,\n\t * }\n\t * }\n\t * ```\n\t */\n\tstatic props?: RecordProps<TLUnknownShape>\n\n\t/**\n\t * Migrations allow you to make changes to a shape's props over time. Read the\n\t * {@link https://www.tldraw.dev/docs/persistence#Shape-props-migrations | shape prop migrations}\n\t * guide for more information.\n\t */\n\tstatic migrations?: LegacyMigrations | TLPropsMigrations | MigrationSequence\n\n\t/**\n\t * The type of the shape util, which should match the shape's type.\n\t *\n\t * @public\n\t */\n\tstatic type: string\n\n\t/**\n\t * Get the default props for a shape.\n\t *\n\t * @public\n\t */\n\tabstract getDefaultProps(): Shape['props']\n\n\t/**\n\t * Get the shape's geometry.\n\t *\n\t * @param shape - The shape.\n\t * @param opts - Additional options for the request.\n\t * @public\n\t */\n\tabstract getGeometry(shape: Shape, opts?: TLGeometryOpts): Geometry2d\n\n\t/**\n\t * Get a JSX element for the shape (as an HTML element).\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tabstract component(shape: Shape): any\n\n\t/**\n\t * Get JSX describing the shape's indicator (as an SVG element).\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tabstract indicator(shape: Shape): any\n\n\t/**\n\t * Get the font faces that should be rendered in the document in order for this shape to render\n\t * correctly.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tgetFontFaces(shape: Shape): TLFontFace[] {\n\t\treturn EMPTY_ARRAY\n\t}\n\n\t/**\n\t * Whether the shape can be snapped to by another shape.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tcanSnap(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be tabbed to.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tcanTabTo(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be scrolled while editing.\n\t *\n\t * @public\n\t */\n\tcanScroll(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can be bound to. See {@link TLShapeUtilCanBindOpts} for details.\n\t *\n\t * @public\n\t */\n\tcanBind(_opts: TLShapeUtilCanBindOpts): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be double clicked to edit.\n\t *\n\t * @public\n\t */\n\tcanEdit(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can be resized.\n\t *\n\t * @public\n\t */\n\tcanResize(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * When the shape is resized, whether the shape's children should also be resized.\n\t *\n\t * @public\n\t */\n\tcanResizeChildren(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be edited in read-only mode.\n\t *\n\t * @public\n\t */\n\tcanEditInReadonly(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can be cropped.\n\t *\n\t * @public\n\t */\n\tcanCrop(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can participate in layout functions such as alignment or distribution.\n\t *\n\t * @param shape - The shape.\n\t * @param info - Additional context information: the type of action causing the layout and the\n\t * @public\n\t *\n\t * @public\n\t */\n\tcanBeLaidOut(_shape: Shape, _info: TLShapeUtilCanBeLaidOutOpts): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Does this shape provide a background for its children? If this is true,\n\t * then any children with a `renderBackground` method will have their\n\t * backgrounds rendered _above_ this shape. Otherwise, the children's\n\t * backgrounds will be rendered above either the next ancestor that provides\n\t * a background, or the canvas background.\n\t *\n\t * @internal\n\t */\n\tprovidesBackgroundForChildren(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its resize handles when selected.\n\t *\n\t * @public\n\t */\n\thideResizeHandles(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its rotation handles when selected.\n\t *\n\t * @public\n\t */\n\thideRotateHandle(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its selection bounds background when selected.\n\t *\n\t * @public\n\t */\n\thideSelectionBoundsBg(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its selection bounds foreground when selected.\n\t *\n\t * @public\n\t */\n\thideSelectionBoundsFg(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape's aspect ratio is locked.\n\t *\n\t * @public\n\t */\n\tisAspectRatioLocked(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Get a JSX element for the shape (as an HTML element) to be rendered as part of the canvas background - behind any other shape content.\n\t *\n\t * @param shape - The shape.\n\t * @internal\n\t */\n\tbackgroundComponent?(shape: Shape): any\n\n\t/**\n\t * Get the interpolated props for an animating shape. This is an optional method.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * util.getInterpolatedProps?.(startShape, endShape, t)\n\t * ```\n\t *\n\t * @param startShape - The initial shape.\n\t * @param endShape - The initial shape.\n\t * @param progress - The normalized progress between zero (start) and 1 (end).\n\t * @public\n\t */\n\tgetInterpolatedProps?(startShape: Shape, endShape: Shape, progress: number): Shape['props']\n\n\t/**\n\t * Get an array of handle models for the shape. This is an optional method.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * util.getHandles?.(myShape)\n\t * ```\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tgetHandles?(shape: Shape): TLHandle[]\n\n\t/**\n\t * Get whether the shape can receive children of a given type.\n\t *\n\t * @param shape - The shape.\n\t * @param type - The shape type.\n\t * @public\n\t */\n\tcanReceiveNewChildrenOfType(_shape: Shape, _type: TLShape['type']) {\n\t\treturn false\n\t}\n\n\t/**\n\t * Get the shape as an SVG object.\n\t *\n\t * @param shape - The shape.\n\t * @param ctx - The export context for the SVG - used for adding e.g. \\<def\\>s\n\t * @returns An SVG element.\n\t * @public\n\t */\n\ttoSvg?(shape: Shape, ctx: SvgExportContext): ReactElement | null | Promise<ReactElement | null>\n\n\t/**\n\t * Get the shape's background layer as an SVG object.\n\t *\n\t * @param shape - The shape.\n\t * @param ctx - ctx - The export context for the SVG - used for adding e.g. \\<def\\>s\n\t * @returns An SVG element.\n\t * @public\n\t */\n\ttoBackgroundSvg?(\n\t\tshape: Shape,\n\t\tctx: SvgExportContext\n\t): ReactElement | null | Promise<ReactElement | null>\n\n\t/** @internal */\n\texpandSelectionOutlinePx(shape: Shape): number | Box {\n\t\treturn 0\n\t}\n\n\t/**\n\t * Return elements to be added to the \\<defs\\> section of the canvases SVG context. This can be\n\t * used to define SVG content (e.g. patterns & masks) that can be referred to by ID from svg\n\t * elements returned by `component`.\n\t *\n\t * Each def should have a unique `key`. If multiple defs from different shapes all have the same\n\t * key, only one will be used.\n\t */\n\tgetCanvasSvgDefs(): TLShapeUtilCanvasSvgDef[] {\n\t\treturn []\n\t}\n\n\t/**\n\t * Get the geometry to use when snapping to this this shape in translate/resize operations. See\n\t * {@link BoundsSnapGeometry} for details.\n\t */\n\tgetBoundsSnapGeometry(_shape: Shape): BoundsSnapGeometry {\n\t\treturn {}\n\t}\n\n\t/**\n\t * Get the geometry to use when snapping handles to this shape. See {@link HandleSnapGeometry}\n\t * for details.\n\t */\n\tgetHandleSnapGeometry(_shape: Shape): HandleSnapGeometry {\n\t\treturn {}\n\t}\n\n\tgetText(_shape: Shape): string | undefined {\n\t\treturn undefined\n\t}\n\n\tgetAriaDescriptor(_shape: Shape): string | undefined {\n\t\treturn undefined\n\t}\n\n\t// Events\n\n\t/**\n\t * A callback called just before a shape is created. This method provides a last chance to modify\n\t * the created shape.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * onBeforeCreate = (next) => {\n\t * \treturn { ...next, x: next.x + 1 }\n\t * }\n\t * ```\n\t *\n\t * @param next - The next shape.\n\t * @returns The next shape or void.\n\t * @public\n\t */\n\tonBeforeCreate?(next: Shape): Shape | void\n\n\t/**\n\t * A callback called just before a shape is updated. This method provides a last chance to modify\n\t * the updated shape.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * onBeforeUpdate = (prev, next) => {\n\t * \tif (prev.x === next.x) {\n\t * \t\treturn { ...next, x: next.x + 1 }\n\t * \t}\n\t * }\n\t * ```\n\t *\n\t * @param prev - The previous shape.\n\t * @param next - The next shape.\n\t * @returns The next shape or void.\n\t * @public\n\t */\n\tonBeforeUpdate?(prev: Shape, next: Shape): Shape | void\n\n\t/**\n\t * A callback called when a shape changes from a crop.\n\t *\n\t * @param shape - The shape at the start of the crop.\n\t * @param info - Info about the crop.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonCrop?(\n\t\tshape: Shape,\n\t\tinfo: TLCropInfo<Shape>\n\t): Omit<TLShapePartial<Shape>, 'id' | 'type'> | undefined | void\n\n\t/**\n\t * A callback called when some other shapes are dragged into this one. This fires when the shapes are dragged over the shape for the first time.\n\t *\n\t * @param shape - The shape.\n\t * @param shapes - The shapes that are being dragged in.\n\t * @public\n\t */\n\tonDragShapesIn?(shape: Shape, shapes: TLShape[], info: TLDragShapesInInfo): void\n\n\t/**\n\t * A callback called when some other shapes are dragged over this one. This fires when the shapes are dragged over the shape for the first time (after the onDragShapesIn callback), and again on every update while the shapes are being dragged.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * onDragShapesOver = (shape, shapes) => {\n\t * \tthis.editor.reparentShapes(shapes, shape.id)\n\t * }\n\t * ```\n\t *\n\t * @param shape - The shape.\n\t * @param shapes - The shapes that are being dragged over this one.\n\t * @public\n\t */\n\tonDragShapesOver?(shape: Shape, shapes: TLShape[], info: TLDragShapesOverInfo): void\n\n\t/**\n\t * A callback called when some other shapes are dragged out of this one.\n\t *\n\t * @param shape - The shape.\n\t * @param shapes - The shapes that are being dragged out.\n\t * @public\n\t */\n\tonDragShapesOut?(shape: Shape, shapes: TLShape[], info: TLDragShapesOutInfo): void\n\n\t/**\n\t * A callback called when some other shapes are dropped over this one.\n\t *\n\t * @param shape - The shape.\n\t * @param shapes - The shapes that are being dropped over this one.\n\t * @public\n\t */\n\tonDropShapesOver?(shape: Shape, shapes: TLShape[], info: TLDropShapesOverInfo): void\n\n\t/**\n\t * A callback called when a shape starts being resized.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonResizeStart?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape changes from a resize.\n\t *\n\t * @param shape - The shape at the start of the resize.\n\t * @param info - Info about the resize.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonResize?(\n\t\tshape: Shape,\n\t\tinfo: TLResizeInfo<Shape>\n\t): Omit<TLShapePartial<Shape>, 'id' | 'type'> | undefined | void\n\n\t/**\n\t * A callback called when a shape finishes resizing.\n\t *\n\t * @param initial - The shape at the start of the resize.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonResizeEnd?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape starts being translated.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonTranslateStart?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape changes from a translation.\n\t *\n\t * @param initial - The shape at the start of the translation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonTranslate?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape finishes translating.\n\t *\n\t * @param initial - The shape at the start of the translation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonTranslateEnd?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's handle changes.\n\t *\n\t * @param shape - The current shape.\n\t * @param info - An object containing the handle and whether the handle is 'precise' or not.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonHandleDrag?(shape: Shape, info: TLHandleDragInfo<Shape>): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape starts being rotated.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonRotateStart?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape changes from a rotation.\n\t *\n\t * @param initial - The shape at the start of the rotation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonRotate?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape finishes rotating.\n\t *\n\t * @param initial - The shape at the start of the rotation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonRotateEnd?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * Not currently used.\n\t *\n\t * @internal\n\t */\n\tonBindingChange?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's children change.\n\t *\n\t * @param shape - The shape.\n\t * @returns An array of shape updates, or void.\n\t * @public\n\t */\n\tonChildrenChange?(shape: Shape): TLShapePartial[] | void\n\n\t/**\n\t * A callback called when a shape's handle is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @param handle - The handle that is double-clicked.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClickHandle?(shape: Shape, handle: TLHandle): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's edge is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @param info - Info about the edge.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClickEdge?(shape: Shape, info: TLClickEventInfo): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's corner is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @param info - Info about the corner.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClickCorner?(shape: Shape, info: TLClickEventInfo): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClick?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape is clicked.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonClick?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape starts being edited.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tonEditStart?(shape: Shape): void\n\n\t/**\n\t * A callback called when a shape finishes being edited.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tonEditEnd?(shape: Shape): void\n}\n\n/**\n * Info about a crop.\n * @param handle - The handle being dragged.\n * @param change - The distance the handle is moved.\n * @param initialShape - The shape at the start of the resize.\n * @public\n */\nexport interface TLCropInfo<T extends TLShape> {\n\thandle: SelectionHandle\n\tchange: Vec\n\tcrop: TLShapeCrop\n\tuncroppedSize: { w: number; h: number }\n\tinitialShape: T\n\taspectRatioLocked?: boolean\n}\n\n/** @public */\nexport interface TLDragShapesInInfo {\n\tinitialDraggingOverShapeId: TLShapeId | null\n\tprevDraggingOverShapeId: TLShapeId | null\n\tinitialParentIds: Map<TLShapeId, TLParentId>\n\tinitialIndices: Map<TLShapeId, IndexKey>\n}\n\n/** @public */\nexport interface TLDragShapesOverInfo {\n\tinitialDraggingOverShapeId: TLShapeId | null\n\tinitialParentIds: Map<TLShapeId, TLParentId>\n\tinitialIndices: Map<TLShapeId, IndexKey>\n}\n\n/** @public */\nexport interface TLDragShapesOutInfo {\n\tnextDraggingOverShapeId: TLShapeId | null\n\tinitialDraggingOverShapeId: TLShapeId | null\n\tinitialParentIds: Map<TLShapeId, TLParentId>\n\tinitialIndices: Map<TLShapeId, IndexKey>\n}\n\n/** @public */\nexport interface TLDropShapesOverInfo {\n\tinitialDraggingOverShapeId: TLShapeId | null\n\tinitialParentIds: Map<TLShapeId, TLParentId>\n\tinitialIndices: Map<TLShapeId, IndexKey>\n}\n\n/**\n * The type of resize.\n *\n * 'scale_shape' - The shape is being scaled, usually as part of a larger selection.\n *\n * 'resize_bounds' - The user is directly manipulating an individual shape's bounds using a resize\n * handle. It is up to shape util implementers to decide how they want to handle the two\n * situations.\n *\n * @public\n */\nexport type TLResizeMode = 'scale_shape' | 'resize_bounds'\n\n/**\n * Info about a resize.\n * @param newPoint - The new local position of the shape.\n * @param handle - The handle being dragged.\n * @param mode - The type of resize.\n * @param scaleX - The scale in the x-axis.\n * @param scaleY - The scale in the y-axis.\n * @param initialBounds - The bounds of the shape at the start of the resize.\n * @param initialShape - The shape at the start of the resize.\n * @public\n */\nexport interface TLResizeInfo<T extends TLShape> {\n\tnewPoint: Vec\n\thandle: TLResizeHandle\n\tmode: TLResizeMode\n\tscaleX: number\n\tscaleY: number\n\tinitialBounds: Box\n\tinitialShape: T\n}\n\n/* -------------------- Dragging -------------------- */\n\n/** @public */\nexport interface TLHandleDragInfo<T extends TLShape> {\n\thandle: TLHandle\n\tisPrecise: boolean\n\tinitial?: T | undefined\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["/* eslint-disable @typescript-eslint/no-unused-vars */\nimport { EMPTY_ARRAY } from '@tldraw/state'\nimport { LegacyMigrations, MigrationSequence } from '@tldraw/store'\nimport {\n\tRecordProps,\n\tTLHandle,\n\tTLPropsMigrations,\n\tTLShape,\n\tTLShapeCrop,\n\tTLShapePartial,\n\tTLUnknownShape,\n} from '@tldraw/tlschema'\nimport { ReactElement } from 'react'\nimport { Box, SelectionHandle } from '../../primitives/Box'\nimport { Vec } from '../../primitives/Vec'\nimport { Geometry2d } from '../../primitives/geometry/Geometry2d'\nimport type { Editor } from '../Editor'\nimport { TLFontFace } from '../managers/FontManager/FontManager'\nimport { BoundsSnapGeometry } from '../managers/SnapManager/BoundsSnaps'\nimport { HandleSnapGeometry } from '../managers/SnapManager/HandleSnaps'\nimport { SvgExportContext } from '../types/SvgExportContext'\nimport { TLClickEventInfo } from '../types/event-types'\nimport { TLResizeHandle } from '../types/selection-types'\n\n/** @public */\nexport interface TLShapeUtilConstructor<\n\tT extends TLUnknownShape,\n\tU extends ShapeUtil<T> = ShapeUtil<T>,\n> {\n\tnew (editor: Editor): U\n\ttype: T['type']\n\tprops?: RecordProps<T>\n\tmigrations?: LegacyMigrations | TLPropsMigrations | MigrationSequence\n}\n\n/**\n * Options passed to {@link ShapeUtil.canBind}. A binding that could be made. At least one of\n * `fromShapeType` or `toShapeType` will belong to this shape util.\n *\n * @public\n */\nexport interface TLShapeUtilCanBindOpts<Shape extends TLUnknownShape = TLUnknownShape> {\n\t/** The type of shape referenced by the `fromId` of the binding. */\n\tfromShapeType: string\n\t/** The type of shape referenced by the `toId` of the binding. */\n\ttoShapeType: string\n\t/** The type of binding. */\n\tbindingType: string\n}\n\n/**\n * Options passed to {@link ShapeUtil.canBeLaidOut}.\n *\n * @public\n */\nexport interface TLShapeUtilCanBeLaidOutOpts {\n\t/** The type of action causing the layout. */\n\ttype?: 'align' | 'distribute' | 'pack' | 'stack' | 'flip' | 'stretch'\n\t/** The other shapes being laid out */\n\tshapes?: TLShape[]\n}\n\n/** Additional options for the {@link ShapeUtil.getGeometry} method.\n *\n * @public\n */\nexport interface TLGeometryOpts {\n\t/** The context in which the geometry is being requested. */\n\tcontext?: string\n}\n\n/** @public */\nexport interface TLShapeUtilCanvasSvgDef {\n\tkey: string\n\tcomponent: React.ComponentType\n}\n\n/** @public */\nexport abstract class ShapeUtil<Shape extends TLUnknownShape = TLUnknownShape> {\n\t/** Configure this shape utils {@link ShapeUtil.options | `options`}. */\n\tstatic configure<T extends TLShapeUtilConstructor<any, any>>(\n\t\tthis: T,\n\t\toptions: T extends new (...args: any[]) => { options: infer Options } ? Partial<Options> : never\n\t): T {\n\t\t// @ts-expect-error -- typescript has no idea what's going on here but it's fine\n\t\treturn class extends this {\n\t\t\t// @ts-expect-error\n\t\t\toptions = { ...this.options, ...options }\n\t\t}\n\t}\n\n\tconstructor(public editor: Editor) {}\n\n\t/**\n\t * Options for this shape util. If you're implementing a custom shape util, you can override\n\t * this to provide customization options for your shape. If using an existing shape util, you\n\t * can customizing this by calling {@link ShapeUtil.configure}.\n\t */\n\toptions = {}\n\n\t/**\n\t * Props allow you to define the shape's properties in a way that the editor can understand.\n\t * This has two main uses:\n\t *\n\t * 1. Validation. Shapes will be validated using these props to stop bad data from being saved.\n\t * 2. Styles. Each {@link @tldraw/tlschema#StyleProp} in the props can be set on many shapes at\n\t * once, and will be remembered from one shape to the next.\n\t *\n\t * @example\n\t * ```tsx\n\t * import {T, TLBaseShape, TLDefaultColorStyle, DefaultColorStyle, ShapeUtil} from 'tldraw'\n\t *\n\t * type MyShape = TLBaseShape<'mine', {\n\t * color: TLDefaultColorStyle,\n\t * text: string,\n\t * }>\n\t *\n\t * class MyShapeUtil extends ShapeUtil<MyShape> {\n\t * static props = {\n\t * // we use tldraw's built-in color style:\n\t * color: DefaultColorStyle,\n\t * // validate that the text prop is a string:\n\t * text: T.string,\n\t * }\n\t * }\n\t * ```\n\t */\n\tstatic props?: RecordProps<TLUnknownShape>\n\n\t/**\n\t * Migrations allow you to make changes to a shape's props over time. Read the\n\t * {@link https://www.tldraw.dev/docs/persistence#Shape-props-migrations | shape prop migrations}\n\t * guide for more information.\n\t */\n\tstatic migrations?: LegacyMigrations | TLPropsMigrations | MigrationSequence\n\n\t/**\n\t * The type of the shape util, which should match the shape's type.\n\t *\n\t * @public\n\t */\n\tstatic type: string\n\n\t/**\n\t * Get the default props for a shape.\n\t *\n\t * @public\n\t */\n\tabstract getDefaultProps(): Shape['props']\n\n\t/**\n\t * Get the shape's geometry.\n\t *\n\t * @param shape - The shape.\n\t * @param opts - Additional options for the request.\n\t * @public\n\t */\n\tabstract getGeometry(shape: Shape, opts?: TLGeometryOpts): Geometry2d\n\n\t/**\n\t * Get a JSX element for the shape (as an HTML element).\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tabstract component(shape: Shape): any\n\n\t/**\n\t * Get JSX describing the shape's indicator (as an SVG element).\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tabstract indicator(shape: Shape): any\n\n\t/**\n\t * Get the font faces that should be rendered in the document in order for this shape to render\n\t * correctly.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tgetFontFaces(shape: Shape): TLFontFace[] {\n\t\treturn EMPTY_ARRAY\n\t}\n\n\t/**\n\t * Whether the shape can be snapped to by another shape.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tcanSnap(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be tabbed to.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tcanTabTo(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be scrolled while editing.\n\t *\n\t * @public\n\t */\n\tcanScroll(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can be bound to. See {@link TLShapeUtilCanBindOpts} for details.\n\t *\n\t * @public\n\t */\n\tcanBind(_opts: TLShapeUtilCanBindOpts): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be double clicked to edit.\n\t *\n\t * @public\n\t */\n\tcanEdit(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can be resized.\n\t *\n\t * @public\n\t */\n\tcanResize(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * When the shape is resized, whether the shape's children should also be resized.\n\t *\n\t * @public\n\t */\n\tcanResizeChildren(_shape: Shape): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Whether the shape can be edited in read-only mode.\n\t *\n\t * @public\n\t */\n\tcanEditInReadonly(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can be cropped.\n\t *\n\t * @public\n\t */\n\tcanCrop(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape can participate in layout functions such as alignment or distribution.\n\t *\n\t * @param shape - The shape.\n\t * @param info - Additional context information: the type of action causing the layout and the\n\t * @public\n\t *\n\t * @public\n\t */\n\tcanBeLaidOut(_shape: Shape, _info: TLShapeUtilCanBeLaidOutOpts): boolean {\n\t\treturn true\n\t}\n\n\t/**\n\t * Does this shape provide a background for its children? If this is true,\n\t * then any children with a `renderBackground` method will have their\n\t * backgrounds rendered _above_ this shape. Otherwise, the children's\n\t * backgrounds will be rendered above either the next ancestor that provides\n\t * a background, or the canvas background.\n\t *\n\t * @internal\n\t */\n\tprovidesBackgroundForChildren(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its resize handles when selected.\n\t *\n\t * @public\n\t */\n\thideResizeHandles(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its rotation handles when selected.\n\t *\n\t * @public\n\t */\n\thideRotateHandle(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its selection bounds background when selected.\n\t *\n\t * @public\n\t */\n\thideSelectionBoundsBg(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape should hide its selection bounds foreground when selected.\n\t *\n\t * @public\n\t */\n\thideSelectionBoundsFg(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Whether the shape's aspect ratio is locked.\n\t *\n\t * @public\n\t */\n\tisAspectRatioLocked(_shape: Shape): boolean {\n\t\treturn false\n\t}\n\n\t/**\n\t * Get a JSX element for the shape (as an HTML element) to be rendered as part of the canvas background - behind any other shape content.\n\t *\n\t * @param shape - The shape.\n\t * @internal\n\t */\n\tbackgroundComponent?(shape: Shape): any\n\n\t/**\n\t * Get the interpolated props for an animating shape. This is an optional method.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * util.getInterpolatedProps?.(startShape, endShape, t)\n\t * ```\n\t *\n\t * @param startShape - The initial shape.\n\t * @param endShape - The initial shape.\n\t * @param progress - The normalized progress between zero (start) and 1 (end).\n\t * @public\n\t */\n\tgetInterpolatedProps?(startShape: Shape, endShape: Shape, progress: number): Shape['props']\n\n\t/**\n\t * Get an array of handle models for the shape. This is an optional method.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * util.getHandles?.(myShape)\n\t * ```\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tgetHandles?(shape: Shape): TLHandle[]\n\n\t/**\n\t * Get whether the shape can receive children of a given type.\n\t *\n\t * @param shape - The shape.\n\t * @param type - The shape type.\n\t * @public\n\t */\n\tcanReceiveNewChildrenOfType(_shape: Shape, _type: TLShape['type']) {\n\t\treturn false\n\t}\n\n\t/**\n\t * Get whether the shape can receive children of a given type.\n\t *\n\t * @param shape - The shape type.\n\t * @param shapes - The shapes that are being dropped.\n\t * @public\n\t */\n\tcanDropShapes(_shape: Shape, _shapes: TLShape[]) {\n\t\treturn false\n\t}\n\n\t/**\n\t * Get the shape as an SVG object.\n\t *\n\t * @param shape - The shape.\n\t * @param ctx - The export context for the SVG - used for adding e.g. \\<def\\>s\n\t * @returns An SVG element.\n\t * @public\n\t */\n\ttoSvg?(shape: Shape, ctx: SvgExportContext): ReactElement | null | Promise<ReactElement | null>\n\n\t/**\n\t * Get the shape's background layer as an SVG object.\n\t *\n\t * @param shape - The shape.\n\t * @param ctx - ctx - The export context for the SVG - used for adding e.g. \\<def\\>s\n\t * @returns An SVG element.\n\t * @public\n\t */\n\ttoBackgroundSvg?(\n\t\tshape: Shape,\n\t\tctx: SvgExportContext\n\t): ReactElement | null | Promise<ReactElement | null>\n\n\t/** @internal */\n\texpandSelectionOutlinePx(shape: Shape): number | Box {\n\t\treturn 0\n\t}\n\n\t/**\n\t * Return elements to be added to the \\<defs\\> section of the canvases SVG context. This can be\n\t * used to define SVG content (e.g. patterns & masks) that can be referred to by ID from svg\n\t * elements returned by `component`.\n\t *\n\t * Each def should have a unique `key`. If multiple defs from different shapes all have the same\n\t * key, only one will be used.\n\t */\n\tgetCanvasSvgDefs(): TLShapeUtilCanvasSvgDef[] {\n\t\treturn []\n\t}\n\n\t/**\n\t * Get the geometry to use when snapping to this this shape in translate/resize operations. See\n\t * {@link BoundsSnapGeometry} for details.\n\t */\n\tgetBoundsSnapGeometry(_shape: Shape): BoundsSnapGeometry {\n\t\treturn {}\n\t}\n\n\t/**\n\t * Get the geometry to use when snapping handles to this shape. See {@link HandleSnapGeometry}\n\t * for details.\n\t */\n\tgetHandleSnapGeometry(_shape: Shape): HandleSnapGeometry {\n\t\treturn {}\n\t}\n\n\tgetText(_shape: Shape): string | undefined {\n\t\treturn undefined\n\t}\n\n\tgetAriaDescriptor(_shape: Shape): string | undefined {\n\t\treturn undefined\n\t}\n\n\t// Events\n\n\t/**\n\t * A callback called just before a shape is created. This method provides a last chance to modify\n\t * the created shape.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * onBeforeCreate = (next) => {\n\t * \treturn { ...next, x: next.x + 1 }\n\t * }\n\t * ```\n\t *\n\t * @param next - The next shape.\n\t * @returns The next shape or void.\n\t * @public\n\t */\n\tonBeforeCreate?(next: Shape): Shape | void\n\n\t/**\n\t * A callback called just before a shape is updated. This method provides a last chance to modify\n\t * the updated shape.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * onBeforeUpdate = (prev, next) => {\n\t * \tif (prev.x === next.x) {\n\t * \t\treturn { ...next, x: next.x + 1 }\n\t * \t}\n\t * }\n\t * ```\n\t *\n\t * @param prev - The previous shape.\n\t * @param next - The next shape.\n\t * @returns The next shape or void.\n\t * @public\n\t */\n\tonBeforeUpdate?(prev: Shape, next: Shape): Shape | void\n\n\t/**\n\t * A callback called when a shape changes from a crop.\n\t *\n\t * @param shape - The shape at the start of the crop.\n\t * @param info - Info about the crop.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonCrop?(\n\t\tshape: Shape,\n\t\tinfo: TLCropInfo<Shape>\n\t): Omit<TLShapePartial<Shape>, 'id' | 'type'> | undefined | void\n\n\t/**\n\t * A callback called when some other shapes are dragged over this one.\n\t *\n\t * @example\n\t *\n\t * ```ts\n\t * onDragShapesOver = (shape, shapes) => {\n\t * \tthis.editor.reparentShapes(shapes, shape.id)\n\t * }\n\t * ```\n\t *\n\t * @param shape - The shape.\n\t * @param shapes - The shapes that are being dragged over this one.\n\t * @public\n\t */\n\tonDragShapesOver?(shape: Shape, shapes: TLShape[]): void\n\n\t/**\n\t * A callback called when some other shapes are dragged out of this one.\n\t *\n\t * @param shape - The shape.\n\t * @param shapes - The shapes that are being dragged out.\n\t * @public\n\t */\n\tonDragShapesOut?(shape: Shape, shapes: TLShape[]): void\n\n\t/**\n\t * A callback called when some other shapes are dropped over this one.\n\t *\n\t * @param shape - The shape.\n\t * @param shapes - The shapes that are being dropped over this one.\n\t * @public\n\t */\n\tonDropShapesOver?(shape: Shape, shapes: TLShape[]): void\n\n\t/**\n\t * A callback called when a shape starts being resized.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonResizeStart?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape changes from a resize.\n\t *\n\t * @param shape - The shape at the start of the resize.\n\t * @param info - Info about the resize.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonResize?(\n\t\tshape: Shape,\n\t\tinfo: TLResizeInfo<Shape>\n\t): Omit<TLShapePartial<Shape>, 'id' | 'type'> | undefined | void\n\n\t/**\n\t * A callback called when a shape finishes resizing.\n\t *\n\t * @param initial - The shape at the start of the resize.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonResizeEnd?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape starts being translated.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonTranslateStart?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape changes from a translation.\n\t *\n\t * @param initial - The shape at the start of the translation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonTranslate?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape finishes translating.\n\t *\n\t * @param initial - The shape at the start of the translation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonTranslateEnd?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's handle changes.\n\t *\n\t * @param shape - The current shape.\n\t * @param info - An object containing the handle and whether the handle is 'precise' or not.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonHandleDrag?(shape: Shape, info: TLHandleDragInfo<Shape>): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape starts being rotated.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonRotateStart?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape changes from a rotation.\n\t *\n\t * @param initial - The shape at the start of the rotation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonRotate?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape finishes rotating.\n\t *\n\t * @param initial - The shape at the start of the rotation.\n\t * @param current - The current shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonRotateEnd?(initial: Shape, current: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * Not currently used.\n\t *\n\t * @internal\n\t */\n\tonBindingChange?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's children change.\n\t *\n\t * @param shape - The shape.\n\t * @returns An array of shape updates, or void.\n\t * @public\n\t */\n\tonChildrenChange?(shape: Shape): TLShapePartial[] | void\n\n\t/**\n\t * A callback called when a shape's handle is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @param handle - The handle that is double-clicked.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClickHandle?(shape: Shape, handle: TLHandle): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's edge is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @param info - Info about the edge.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClickEdge?(shape: Shape, info: TLClickEventInfo): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape's corner is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @param info - Info about the corner.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClickCorner?(shape: Shape, info: TLClickEventInfo): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape is double clicked.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonDoubleClick?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape is clicked.\n\t *\n\t * @param shape - The shape.\n\t * @returns A change to apply to the shape, or void.\n\t * @public\n\t */\n\tonClick?(shape: Shape): TLShapePartial<Shape> | void\n\n\t/**\n\t * A callback called when a shape starts being edited.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tonEditStart?(shape: Shape): void\n\n\t/**\n\t * A callback called when a shape finishes being edited.\n\t *\n\t * @param shape - The shape.\n\t * @public\n\t */\n\tonEditEnd?(shape: Shape): void\n}\n\n/**\n * Info about a crop.\n * @param handle - The handle being dragged.\n * @param change - The distance the handle is moved.\n * @param initialShape - The shape at the start of the resize.\n * @public\n */\nexport interface TLCropInfo<T extends TLShape> {\n\thandle: SelectionHandle\n\tchange: Vec\n\tcrop: TLShapeCrop\n\tuncroppedSize: { w: number; h: number }\n\tinitialShape: T\n\taspectRatioLocked?: boolean\n}\n\n/**\n * The type of resize.\n *\n * 'scale_shape' - The shape is being scaled, usually as part of a larger selection.\n *\n * 'resize_bounds' - The user is directly manipulating an individual shape's bounds using a resize\n * handle. It is up to shape util implementers to decide how they want to handle the two\n * situations.\n *\n * @public\n */\nexport type TLResizeMode = 'scale_shape' | 'resize_bounds'\n\n/**\n * Info about a resize.\n * @param newPoint - The new local position of the shape.\n * @param handle - The handle being dragged.\n * @param mode - The type of resize.\n * @param scaleX - The scale in the x-axis.\n * @param scaleY - The scale in the y-axis.\n * @param initialBounds - The bounds of the shape at the start of the resize.\n * @param initialShape - The shape at the start of the resize.\n * @public\n */\nexport interface TLResizeInfo<T extends TLShape> {\n\tnewPoint: Vec\n\thandle: TLResizeHandle\n\tmode: TLResizeMode\n\tscaleX: number\n\tscaleY: number\n\tinitialBounds: Box\n\tinitialShape: T\n}\n\n/* -------------------- Dragging -------------------- */\n\n/** @public */\nexport interface TLHandleDragInfo<T extends TLShape> {\n\thandle: TLHandle\n\tisPrecise: boolean\n\tinitial?: T | undefined\n}\n"],
5
+ "mappings": "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",
6
6
  "names": []
7
7
  }
@@ -29,13 +29,12 @@ var import_StateNode = require("../../StateNode");
29
29
  class Pointing extends import_StateNode.StateNode {
30
30
  static id = "pointing";
31
31
  onPointerMove(info) {
32
- const { editor } = this;
33
- if (editor.inputs.isDragging) {
34
- const { originPagePoint } = editor.inputs;
32
+ if (this.editor.inputs.isDragging) {
33
+ const { originPagePoint } = this.editor.inputs;
35
34
  const shapeType = this.parent.shapeType;
36
35
  const id = (0, import_tlschema.createShapeId)();
37
- const creatingMarkId = editor.markHistoryStoppingPoint(`creating_box:${id}`);
38
- const newPoint = maybeSnapToGrid(originPagePoint, editor);
36
+ const creatingMarkId = this.editor.markHistoryStoppingPoint(`creating_box:${id}`);
37
+ const newPoint = maybeSnapToGrid(originPagePoint, this.editor);
39
38
  this.editor.createShapes([
40
39
  {
41
40
  id,
@@ -47,13 +46,7 @@ class Pointing extends import_StateNode.StateNode {
47
46
  h: 1
48
47
  }
49
48
  }
50
- ]);
51
- const shape = editor.getShape(id);
52
- if (!shape) {
53
- this.cancel();
54
- return;
55
- }
56
- editor.select(id);
49
+ ]).select(id);
57
50
  const parent = this.parent;
58
51
  this.editor.setCurrentTool(
59
52
  "select.resizing",
@@ -65,7 +58,7 @@ class Pointing extends import_StateNode.StateNode {
65
58
  creatingMarkId,
66
59
  creationCursorOffset: { x: 1, y: 1 },
67
60
  onInteractionEnd: this.parent.id,
68
- onCreate: parent.onCreate ? (shape2) => parent.onCreate?.(shape2) : void 0
61
+ onCreate: parent.onCreate ? (shape) => parent.onCreate?.(shape) : void 0
69
62
  }
70
63
  /** satisfies ResizingInfo, defined in main tldraw package 😧 */
71
64
  );
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../../../src/lib/editor/tools/BaseBoxShapeTool/children/Pointing.ts"],
4
- "sourcesContent": ["import { TLShape, createShapeId } from '@tldraw/tlschema'\nimport { structuredClone } from '@tldraw/utils'\nimport { Vec } from '../../../../primitives/Vec'\nimport { Editor } from '../../../Editor'\nimport { TLBaseBoxShape } from '../../../shapes/BaseBoxShapeUtil'\nimport { TLPointerEventInfo } from '../../../types/event-types'\nimport { StateNode } from '../../StateNode'\nimport { BaseBoxShapeTool } from '../BaseBoxShapeTool'\n\nexport class Pointing extends StateNode {\n\tstatic override id = 'pointing'\n\n\toverride onPointerMove(info: TLPointerEventInfo) {\n\t\tconst { editor } = this\n\t\tif (editor.inputs.isDragging) {\n\t\t\tconst { originPagePoint } = editor.inputs\n\n\t\t\tconst shapeType = (this.parent as BaseBoxShapeTool)!.shapeType\n\n\t\t\tconst id = createShapeId()\n\n\t\t\tconst creatingMarkId = editor.markHistoryStoppingPoint(`creating_box:${id}`)\n\t\t\tconst newPoint = maybeSnapToGrid(originPagePoint, editor)\n\n\t\t\t// Allow this to trigger the max shapes reached alert\n\t\t\tthis.editor.createShapes<TLBaseBoxShape>([\n\t\t\t\t{\n\t\t\t\t\tid,\n\t\t\t\t\ttype: shapeType,\n\t\t\t\t\tx: newPoint.x,\n\t\t\t\t\ty: newPoint.y,\n\t\t\t\t\tprops: {\n\t\t\t\t\t\tw: 1,\n\t\t\t\t\t\th: 1,\n\t\t\t\t\t},\n\t\t\t\t},\n\t\t\t])\n\t\t\tconst shape = editor.getShape(id)\n\t\t\tif (!shape) {\n\t\t\t\tthis.cancel()\n\t\t\t\treturn\n\t\t\t}\n\t\t\teditor.select(id)\n\n\t\t\tconst parent = this.parent as BaseBoxShapeTool\n\t\t\tthis.editor.setCurrentTool(\n\t\t\t\t'select.resizing',\n\t\t\t\t{\n\t\t\t\t\t...info,\n\t\t\t\t\ttarget: 'selection',\n\t\t\t\t\thandle: 'bottom_right',\n\t\t\t\t\tisCreating: true,\n\t\t\t\t\tcreatingMarkId,\n\t\t\t\t\tcreationCursorOffset: { x: 1, y: 1 },\n\t\t\t\t\tonInteractionEnd: this.parent.id,\n\t\t\t\t\tonCreate: parent.onCreate\n\t\t\t\t\t\t? (shape: TLShape | null) => parent.onCreate?.(shape)\n\t\t\t\t\t\t: undefined,\n\t\t\t\t} /** satisfies ResizingInfo, defined in main tldraw package \uD83D\uDE27 */\n\t\t\t)\n\t\t}\n\t}\n\n\toverride onPointerUp() {\n\t\tthis.complete()\n\t}\n\n\toverride onCancel() {\n\t\tthis.cancel()\n\t}\n\n\toverride onComplete() {\n\t\tthis.complete()\n\t}\n\n\toverride onInterrupt() {\n\t\tthis.cancel()\n\t}\n\n\tcomplete() {\n\t\tconst { originPagePoint } = this.editor.inputs\n\n\t\tconst shapeType = (this.parent as BaseBoxShapeTool)!.shapeType as TLBaseBoxShape['type']\n\n\t\tconst id = createShapeId()\n\n\t\tthis.editor.markHistoryStoppingPoint(`creating_box:${id}`)\n\n\t\t// Allow this to trigger the max shapes reached alert\n\t\t// todo: add scale here when dynamic size is enabled (is this still needed?)\n\t\tthis.editor.createShapes<TLBaseBoxShape>([\n\t\t\t{\n\t\t\t\tid,\n\t\t\t\ttype: shapeType,\n\t\t\t\tx: originPagePoint.x,\n\t\t\t\ty: originPagePoint.y,\n\t\t\t},\n\t\t])\n\n\t\tconst shape = this.editor.getShape<TLBaseBoxShape>(id)!\n\t\tif (!shape) {\n\t\t\tthis.cancel()\n\t\t\treturn\n\t\t}\n\n\t\tlet { w, h } = shape.props\n\t\tconst delta = new Vec(w / 2, h / 2)\n\t\tconst parentTransform = this.editor.getShapeParentTransform(shape)\n\t\tif (parentTransform) delta.rot(-parentTransform.rotation())\n\t\tlet scale = 1\n\n\t\tif (this.editor.user.getIsDynamicResizeMode()) {\n\t\t\tscale = 1 / this.editor.getZoomLevel()\n\t\t\tw *= scale\n\t\t\th *= scale\n\t\t\tdelta.mul(scale)\n\t\t}\n\n\t\tconst next = structuredClone(shape)\n\t\tconst newPoint = maybeSnapToGrid(new Vec(shape.x - delta.x, shape.y - delta.y), this.editor)\n\t\tnext.x = newPoint.x\n\t\tnext.y = newPoint.y\n\t\tnext.props.w = w\n\t\tnext.props.h = h\n\n\t\tif ('scale' in shape.props) {\n\t\t\t;(next as TLBaseBoxShape & { props: { scale: number } }).props.scale = scale\n\t\t}\n\n\t\tthis.editor.updateShape<TLBaseBoxShape>(next)\n\n\t\tthis.editor.setSelectedShapes([id])\n\n\t\tif (this.editor.getInstanceState().isToolLocked) {\n\t\t\tthis.parent.transition('idle')\n\t\t} else {\n\t\t\tthis.editor.setCurrentTool('select.idle')\n\t\t}\n\t}\n\n\tcancel() {\n\t\tthis.parent.transition('idle')\n\t}\n}\n\n/**\n * Checks if grid mode is enabled and snaps a point to the grid if so\n *\n * @public\n */\nexport function maybeSnapToGrid(point: Vec, editor: Editor): Vec {\n\tconst isGridMode = editor.getInstanceState().isGridMode\n\tconst gridSize = editor.getDocumentSettings().gridSize\n\tif (isGridMode) return point.clone().snapToGrid(gridSize)\n\treturn point.clone()\n}\n"],
5
- "mappings": "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",
6
- "names": ["shape"]
4
+ "sourcesContent": ["import { TLShape, createShapeId } from '@tldraw/tlschema'\nimport { structuredClone } from '@tldraw/utils'\nimport { Vec } from '../../../../primitives/Vec'\nimport { Editor } from '../../../Editor'\nimport { TLBaseBoxShape } from '../../../shapes/BaseBoxShapeUtil'\nimport { TLPointerEventInfo } from '../../../types/event-types'\nimport { StateNode } from '../../StateNode'\nimport { BaseBoxShapeTool } from '../BaseBoxShapeTool'\n\nexport class Pointing extends StateNode {\n\tstatic override id = 'pointing'\n\n\toverride onPointerMove(info: TLPointerEventInfo) {\n\t\tif (this.editor.inputs.isDragging) {\n\t\t\tconst { originPagePoint } = this.editor.inputs\n\n\t\t\tconst shapeType = (this.parent as BaseBoxShapeTool)!.shapeType\n\n\t\t\tconst id = createShapeId()\n\n\t\t\tconst creatingMarkId = this.editor.markHistoryStoppingPoint(`creating_box:${id}`)\n\t\t\tconst newPoint = maybeSnapToGrid(originPagePoint, this.editor)\n\t\t\tthis.editor\n\t\t\t\t.createShapes<TLBaseBoxShape>([\n\t\t\t\t\t{\n\t\t\t\t\t\tid,\n\t\t\t\t\t\ttype: shapeType,\n\t\t\t\t\t\tx: newPoint.x,\n\t\t\t\t\t\ty: newPoint.y,\n\t\t\t\t\t\tprops: {\n\t\t\t\t\t\t\tw: 1,\n\t\t\t\t\t\t\th: 1,\n\t\t\t\t\t\t},\n\t\t\t\t\t},\n\t\t\t\t])\n\t\t\t\t.select(id)\n\n\t\t\tconst parent = this.parent as BaseBoxShapeTool\n\t\t\tthis.editor.setCurrentTool(\n\t\t\t\t'select.resizing',\n\t\t\t\t{\n\t\t\t\t\t...info,\n\t\t\t\t\ttarget: 'selection',\n\t\t\t\t\thandle: 'bottom_right',\n\t\t\t\t\tisCreating: true,\n\t\t\t\t\tcreatingMarkId,\n\t\t\t\t\tcreationCursorOffset: { x: 1, y: 1 },\n\t\t\t\t\tonInteractionEnd: this.parent.id,\n\t\t\t\t\tonCreate: parent.onCreate\n\t\t\t\t\t\t? (shape: TLShape | null) => parent.onCreate?.(shape)\n\t\t\t\t\t\t: undefined,\n\t\t\t\t} /** satisfies ResizingInfo, defined in main tldraw package \uD83D\uDE27 */\n\t\t\t)\n\t\t}\n\t}\n\n\toverride onPointerUp() {\n\t\tthis.complete()\n\t}\n\n\toverride onCancel() {\n\t\tthis.cancel()\n\t}\n\n\toverride onComplete() {\n\t\tthis.complete()\n\t}\n\n\toverride onInterrupt() {\n\t\tthis.cancel()\n\t}\n\n\tcomplete() {\n\t\tconst { originPagePoint } = this.editor.inputs\n\n\t\tconst shapeType = (this.parent as BaseBoxShapeTool)!.shapeType as TLBaseBoxShape['type']\n\n\t\tconst id = createShapeId()\n\n\t\tthis.editor.markHistoryStoppingPoint(`creating_box:${id}`)\n\n\t\t// todo: add scale here when dynamic size is enabled (is this still needed?)\n\t\tthis.editor.createShapes<TLBaseBoxShape>([\n\t\t\t{\n\t\t\t\tid,\n\t\t\t\ttype: shapeType,\n\t\t\t\tx: originPagePoint.x,\n\t\t\t\ty: originPagePoint.y,\n\t\t\t},\n\t\t])\n\n\t\tconst shape = this.editor.getShape<TLBaseBoxShape>(id)!\n\t\tif (!shape) {\n\t\t\tthis.cancel()\n\t\t\treturn\n\t\t}\n\n\t\tlet { w, h } = shape.props\n\t\tconst delta = new Vec(w / 2, h / 2)\n\t\tconst parentTransform = this.editor.getShapeParentTransform(shape)\n\t\tif (parentTransform) delta.rot(-parentTransform.rotation())\n\t\tlet scale = 1\n\n\t\tif (this.editor.user.getIsDynamicResizeMode()) {\n\t\t\tscale = 1 / this.editor.getZoomLevel()\n\t\t\tw *= scale\n\t\t\th *= scale\n\t\t\tdelta.mul(scale)\n\t\t}\n\n\t\tconst next = structuredClone(shape)\n\t\tconst newPoint = maybeSnapToGrid(new Vec(shape.x - delta.x, shape.y - delta.y), this.editor)\n\t\tnext.x = newPoint.x\n\t\tnext.y = newPoint.y\n\t\tnext.props.w = w\n\t\tnext.props.h = h\n\n\t\tif ('scale' in shape.props) {\n\t\t\t;(next as TLBaseBoxShape & { props: { scale: number } }).props.scale = scale\n\t\t}\n\n\t\tthis.editor.updateShape<TLBaseBoxShape>(next)\n\n\t\tthis.editor.setSelectedShapes([id])\n\n\t\tif (this.editor.getInstanceState().isToolLocked) {\n\t\t\tthis.parent.transition('idle')\n\t\t} else {\n\t\t\tthis.editor.setCurrentTool('select.idle')\n\t\t}\n\t}\n\n\tcancel() {\n\t\tthis.parent.transition('idle')\n\t}\n}\n\n/**\n * Checks if grid mode is enabled and snaps a point to the grid if so\n *\n * @public\n */\nexport function maybeSnapToGrid(point: Vec, editor: Editor): Vec {\n\tconst isGridMode = editor.getInstanceState().isGridMode\n\tconst gridSize = editor.getDocumentSettings().gridSize\n\tif (isGridMode) return point.clone().snapToGrid(gridSize)\n\treturn point.clone()\n}\n"],
5
+ "mappings": ";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,sBAAuC;AACvC,mBAAgC;AAChC,iBAAoB;AAIpB,uBAA0B;AAGnB,MAAM,iBAAiB,2BAAU;AAAA,EACvC,OAAgB,KAAK;AAAA,EAEZ,cAAc,MAA0B;AAChD,QAAI,KAAK,OAAO,OAAO,YAAY;AAClC,YAAM,EAAE,gBAAgB,IAAI,KAAK,OAAO;AAExC,YAAM,YAAa,KAAK,OAA6B;AAErD,YAAM,SAAK,+BAAc;AAEzB,YAAM,iBAAiB,KAAK,OAAO,yBAAyB,gBAAgB,EAAE,EAAE;AAChF,YAAM,WAAW,gBAAgB,iBAAiB,KAAK,MAAM;AAC7D,WAAK,OACH,aAA6B;AAAA,QAC7B;AAAA,UACC;AAAA,UACA,MAAM;AAAA,UACN,GAAG,SAAS;AAAA,UACZ,GAAG,SAAS;AAAA,UACZ,OAAO;AAAA,YACN,GAAG;AAAA,YACH,GAAG;AAAA,UACJ;AAAA,QACD;AAAA,MACD,CAAC,EACA,OAAO,EAAE;AAEX,YAAM,SAAS,KAAK;AACpB,WAAK,OAAO;AAAA,QACX;AAAA,QACA;AAAA,UACC,GAAG;AAAA,UACH,QAAQ;AAAA,UACR,QAAQ;AAAA,UACR,YAAY;AAAA,UACZ;AAAA,UACA,sBAAsB,EAAE,GAAG,GAAG,GAAG,EAAE;AAAA,UACnC,kBAAkB,KAAK,OAAO;AAAA,UAC9B,UAAU,OAAO,WACd,CAAC,UAA0B,OAAO,WAAW,KAAK,IAClD;AAAA,QACJ;AAAA;AAAA,MACD;AAAA,IACD;AAAA,EACD;AAAA,EAES,cAAc;AACtB,SAAK,SAAS;AAAA,EACf;AAAA,EAES,WAAW;AACnB,SAAK,OAAO;AAAA,EACb;AAAA,EAES,aAAa;AACrB,SAAK,SAAS;AAAA,EACf;AAAA,EAES,cAAc;AACtB,SAAK,OAAO;AAAA,EACb;AAAA,EAEA,WAAW;AACV,UAAM,EAAE,gBAAgB,IAAI,KAAK,OAAO;AAExC,UAAM,YAAa,KAAK,OAA6B;AAErD,UAAM,SAAK,+BAAc;AAEzB,SAAK,OAAO,yBAAyB,gBAAgB,EAAE,EAAE;AAGzD,SAAK,OAAO,aAA6B;AAAA,MACxC;AAAA,QACC;AAAA,QACA,MAAM;AAAA,QACN,GAAG,gBAAgB;AAAA,QACnB,GAAG,gBAAgB;AAAA,MACpB;AAAA,IACD,CAAC;AAED,UAAM,QAAQ,KAAK,OAAO,SAAyB,EAAE;AACrD,QAAI,CAAC,OAAO;AACX,WAAK,OAAO;AACZ;AAAA,IACD;AAEA,QAAI,EAAE,GAAG,EAAE,IAAI,MAAM;AACrB,UAAM,QAAQ,IAAI,eAAI,IAAI,GAAG,IAAI,CAAC;AAClC,UAAM,kBAAkB,KAAK,OAAO,wBAAwB,KAAK;AACjE,QAAI,gBAAiB,OAAM,IAAI,CAAC,gBAAgB,SAAS,CAAC;AAC1D,QAAI,QAAQ;AAEZ,QAAI,KAAK,OAAO,KAAK,uBAAuB,GAAG;AAC9C,cAAQ,IAAI,KAAK,OAAO,aAAa;AACrC,WAAK;AACL,WAAK;AACL,YAAM,IAAI,KAAK;AAAA,IAChB;AAEA,UAAM,WAAO,8BAAgB,KAAK;AAClC,UAAM,WAAW,gBAAgB,IAAI,eAAI,MAAM,IAAI,MAAM,GAAG,MAAM,IAAI,MAAM,CAAC,GAAG,KAAK,MAAM;AAC3F,SAAK,IAAI,SAAS;AAClB,SAAK,IAAI,SAAS;AAClB,SAAK,MAAM,IAAI;AACf,SAAK,MAAM,IAAI;AAEf,QAAI,WAAW,MAAM,OAAO;AAC3B;AAAC,MAAC,KAAuD,MAAM,QAAQ;AAAA,IACxE;AAEA,SAAK,OAAO,YAA4B,IAAI;AAE5C,SAAK,OAAO,kBAAkB,CAAC,EAAE,CAAC;AAElC,QAAI,KAAK,OAAO,iBAAiB,EAAE,cAAc;AAChD,WAAK,OAAO,WAAW,MAAM;AAAA,IAC9B,OAAO;AACN,WAAK,OAAO,eAAe,aAAa;AAAA,IACzC;AAAA,EACD;AAAA,EAEA,SAAS;AACR,SAAK,OAAO,WAAW,MAAM;AAAA,EAC9B;AACD;AAOO,SAAS,gBAAgB,OAAY,QAAqB;AAChE,QAAM,aAAa,OAAO,iBAAiB,EAAE;AAC7C,QAAM,WAAW,OAAO,oBAAoB,EAAE;AAC9C,MAAI,WAAY,QAAO,MAAM,MAAM,EAAE,WAAW,QAAQ;AACxD,SAAO,MAAM,MAAM;AACpB;",
6
+ "names": []
7
7
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../src/lib/editor/types/emit-types.ts"],
4
- "sourcesContent": ["import { HistoryEntry } from '@tldraw/store'\nimport { TLPageId, TLRecord, TLShapeId } from '@tldraw/tlschema'\nimport { TLEventInfo } from './event-types'\n\n/** @public */\nexport interface TLEventMap {\n\t// Lifecycle / Internal\n\tmount: []\n\t'max-shapes': [{ name: string; pageId: TLPageId; count: number }]\n\tchange: [HistoryEntry<TLRecord>]\n\tupdate: []\n\tcrash: [{ error: unknown }]\n\t'stop-camera-animation': []\n\t'stop-following': []\n\t'before-event': [TLEventInfo]\n\tevent: [TLEventInfo]\n\ttick: [number]\n\tframe: [number]\n\t'select-all-text': [{ shapeId: TLShapeId }]\n\t'place-caret': [{ shapeId: TLShapeId; point: { x: number; y: number } }]\n\t'created-shapes': [TLRecord[]]\n\t'edited-shapes': [TLRecord[]]\n\t'deleted-shapes': [TLShapeId[]]\n\tedit: []\n}\n\n/** @public */\nexport type TLEventMapHandler<T extends keyof TLEventMap> = (...args: TLEventMap[T]) => void\n"],
4
+ "sourcesContent": ["import { HistoryEntry } from '@tldraw/store'\nimport { TLPageId, TLRecord, TLShapeId } from '@tldraw/tlschema'\nimport { TLEventInfo } from './event-types'\n\n/** @public */\nexport interface TLEventMap {\n\t// Lifecycle / Internal\n\tmount: []\n\t'max-shapes': [{ name: string; pageId: TLPageId; count: number }]\n\tchange: [HistoryEntry<TLRecord>]\n\tupdate: []\n\tcrash: [{ error: unknown }]\n\t'stop-camera-animation': []\n\t'stop-following': []\n\t'before-event': [TLEventInfo]\n\tevent: [TLEventInfo]\n\ttick: [number]\n\tframe: [number]\n\t'select-all-text': [{ shapeId: TLShapeId }]\n\t'place-caret': [{ shapeId: TLShapeId; point: { x: number; y: number } }]\n}\n\n/** @public */\nexport type TLEventMapHandler<T extends keyof TLEventMap> = (...args: TLEventMap[T]) => void\n"],
5
5
  "mappings": ";;;;;;;;;;;;;;AAAA;AAAA;",
6
6
  "names": []
7
7
  }
@@ -39,23 +39,19 @@ const Geometry2dFilters = {
39
39
  EXCLUDE_INTERNAL: { includeLabels: true, includeInternal: false }
40
40
  };
41
41
  class Geometry2d {
42
- // todo: consider making accessors for these too, so that they can be overridden in subclasses by geometries with more complex logic
43
42
  isFilled = false;
44
43
  isClosed = true;
45
44
  isLabel = false;
46
- isEmptyLabel = false;
47
45
  isInternal = false;
48
46
  debugColor;
49
47
  ignore;
50
48
  constructor(opts) {
51
- const { isLabel = false, isEmptyLabel = false, isInternal = false } = opts;
52
49
  this.isFilled = opts.isFilled;
53
50
  this.isClosed = opts.isClosed;
51
+ this.isLabel = opts.isLabel ?? false;
52
+ this.isInternal = opts.isInternal ?? false;
54
53
  this.debugColor = opts.debugColor;
55
54
  this.ignore = opts.ignore;
56
- this.isLabel = isLabel;
57
- this.isEmptyLabel = isEmptyLabel;
58
- this.isInternal = isInternal;
59
55
  }
60
56
  isExcludedByFilter(filters) {
61
57
  if (!filters) return false;
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../src/lib/primitives/geometry/Geometry2d.ts"],
4
- "sourcesContent": ["import { assert, invLerp } from '@tldraw/utils'\nimport { Box } from '../Box'\nimport { Mat, MatModel } from '../Mat'\nimport { Vec, VecLike } from '../Vec'\nimport {\n\tintersectCirclePolygon,\n\tintersectCirclePolyline,\n\tintersectLineSegmentPolygon,\n\tintersectLineSegmentPolyline,\n\tintersectPolys,\n\tlinesIntersect,\n} from '../intersect'\nimport { approximately, pointInPolygon } from '../utils'\n\n/**\n * Filter geometry within a group.\n *\n * Filters are ignored when called directly on primitive geometries, but can be used to narrow down\n * the results of an operation on `Group2d` geometries.\n *\n * @public\n */\nexport interface Geometry2dFilters {\n\treadonly includeLabels?: boolean\n\treadonly includeInternal?: boolean\n}\n\n/** @public */\nexport const Geometry2dFilters: {\n\tEXCLUDE_NON_STANDARD: Geometry2dFilters\n\tINCLUDE_ALL: Geometry2dFilters\n\tEXCLUDE_LABELS: Geometry2dFilters\n\tEXCLUDE_INTERNAL: Geometry2dFilters\n} = {\n\tEXCLUDE_NON_STANDARD: {\n\t\tincludeLabels: false,\n\t\tincludeInternal: false,\n\t},\n\tINCLUDE_ALL: { includeLabels: true, includeInternal: true },\n\tEXCLUDE_LABELS: { includeLabels: false, includeInternal: true },\n\tEXCLUDE_INTERNAL: { includeLabels: true, includeInternal: false },\n}\n\n/** @public */\nexport interface TransformedGeometry2dOptions {\n\tisLabel?: boolean\n\tisEmptyLabel?: boolean\n\tisInternal?: boolean\n\tdebugColor?: string\n\tignore?: boolean\n}\n\n/** @public */\nexport interface Geometry2dOptions extends TransformedGeometry2dOptions {\n\tisFilled: boolean\n\tisClosed: boolean\n}\n\n/** @public */\nexport abstract class Geometry2d {\n\t// todo: consider making accessors for these too, so that they can be overridden in subclasses by geometries with more complex logic\n\tisFilled = false\n\tisClosed = true\n\tisLabel = false\n\tisEmptyLabel = false\n\tisInternal = false\n\tdebugColor?: string\n\tignore?: boolean\n\n\tconstructor(opts: Geometry2dOptions) {\n\t\tconst { isLabel = false, isEmptyLabel = false, isInternal = false } = opts\n\t\tthis.isFilled = opts.isFilled\n\t\tthis.isClosed = opts.isClosed\n\t\tthis.debugColor = opts.debugColor\n\t\tthis.ignore = opts.ignore\n\t\tthis.isLabel = isLabel\n\t\tthis.isEmptyLabel = isEmptyLabel\n\t\tthis.isInternal = isInternal\n\t}\n\n\tisExcludedByFilter(filters?: Geometry2dFilters) {\n\t\tif (!filters) return false\n\t\tif (this.isLabel && !filters.includeLabels) return true\n\t\tif (this.isInternal && !filters.includeInternal) return true\n\t\treturn false\n\t}\n\n\tabstract getVertices(filters: Geometry2dFilters): Vec[]\n\n\tabstract nearestPoint(point: VecLike, _filters?: Geometry2dFilters): Vec\n\n\thitTestPoint(point: VecLike, margin = 0, hitInside = false, _filters?: Geometry2dFilters) {\n\t\t// First check whether the point is inside\n\t\tif (this.isClosed && (this.isFilled || hitInside) && pointInPolygon(point, this.vertices)) {\n\t\t\treturn true\n\t\t}\n\t\t// Then check whether the distance is within the margin\n\t\treturn Vec.Dist2(point, this.nearestPoint(point)) <= margin * margin\n\t}\n\n\tdistanceToPoint(point: VecLike, hitInside = false, filters?: Geometry2dFilters) {\n\t\treturn (\n\t\t\tVec.Dist(point, this.nearestPoint(point, filters)) *\n\t\t\t(this.isClosed && (this.isFilled || hitInside) && pointInPolygon(point, this.vertices)\n\t\t\t\t? -1\n\t\t\t\t: 1)\n\t\t)\n\t}\n\n\tdistanceToLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\tif (Vec.Equals(A, B)) return this.distanceToPoint(A, false, filters)\n\t\tconst { vertices } = this\n\t\tlet nearest: Vec | undefined\n\t\tlet dist = Infinity\n\t\tlet d: number, p: Vec, q: Vec\n\t\tconst nextLimit = this.isClosed ? vertices.length : vertices.length - 1\n\t\tfor (let i = 0; i < vertices.length; i++) {\n\t\t\tp = vertices[i]\n\t\t\tif (i < nextLimit) {\n\t\t\t\tconst next = vertices[(i + 1) % vertices.length]\n\t\t\t\tif (linesIntersect(A, B, p, next)) return 0\n\t\t\t}\n\t\t\tq = Vec.NearestPointOnLineSegment(A, B, p, true)\n\t\t\td = Vec.Dist2(p, q)\n\t\t\tif (d < dist) {\n\t\t\t\tdist = d\n\t\t\t\tnearest = q\n\t\t\t}\n\t\t}\n\t\tif (!nearest) throw Error('nearest point not found')\n\t\treturn this.isClosed && this.isFilled && pointInPolygon(nearest, this.vertices) ? -dist : dist\n\t}\n\n\thitTestLineSegment(A: VecLike, B: VecLike, distance = 0, filters?: Geometry2dFilters): boolean {\n\t\treturn this.distanceToLineSegment(A, B, filters) <= distance\n\t}\n\n\tintersectLineSegment(A: VecLike, B: VecLike, _filters?: Geometry2dFilters): VecLike[] {\n\t\tconst intersections = this.isClosed\n\t\t\t? intersectLineSegmentPolygon(A, B, this.vertices)\n\t\t\t: intersectLineSegmentPolyline(A, B, this.vertices)\n\n\t\treturn intersections ?? []\n\t}\n\n\tintersectCircle(center: VecLike, radius: number, _filters?: Geometry2dFilters): VecLike[] {\n\t\tconst intersections = this.isClosed\n\t\t\t? intersectCirclePolygon(center, radius, this.vertices)\n\t\t\t: intersectCirclePolyline(center, radius, this.vertices)\n\n\t\treturn intersections ?? []\n\t}\n\n\tintersectPolygon(polygon: VecLike[], _filters?: Geometry2dFilters): VecLike[] {\n\t\treturn intersectPolys(polygon, this.vertices, true, this.isClosed)\n\t}\n\n\tintersectPolyline(polyline: VecLike[], _filters?: Geometry2dFilters): VecLike[] {\n\t\treturn intersectPolys(polyline, this.vertices, false, this.isClosed)\n\t}\n\n\t/**\n\t * Find a point along the edge of the geometry that is a fraction `t` along the entire way round.\n\t */\n\tinterpolateAlongEdge(t: number, _filters?: Geometry2dFilters): Vec {\n\t\tconst { vertices } = this\n\n\t\tif (t <= 0) return vertices[0]\n\n\t\tconst distanceToTravel = t * this.length\n\t\tlet distanceTraveled = 0\n\n\t\tfor (let i = 0; i < (this.isClosed ? vertices.length : vertices.length - 1); i++) {\n\t\t\tconst curr = vertices[i]\n\t\t\tconst next = vertices[(i + 1) % vertices.length]\n\t\t\tconst dist = Vec.Dist(curr, next)\n\t\t\tconst newDistanceTraveled = distanceTraveled + dist\n\t\t\tif (newDistanceTraveled >= distanceToTravel) {\n\t\t\t\tconst p = Vec.Lrp(\n\t\t\t\t\tcurr,\n\t\t\t\t\tnext,\n\t\t\t\t\tinvLerp(distanceTraveled, newDistanceTraveled, distanceToTravel)\n\t\t\t\t)\n\t\t\t\treturn p\n\t\t\t}\n\t\t\tdistanceTraveled = newDistanceTraveled\n\t\t}\n\n\t\treturn this.isClosed ? vertices[0] : vertices[vertices.length - 1]\n\t}\n\n\t/**\n\t * Take `point`, find the closest point to it on the edge of the geometry, and return how far\n\t * along the edge it is as a fraction of the total length.\n\t */\n\tuninterpolateAlongEdge(point: VecLike, _filters?: Geometry2dFilters): number {\n\t\tconst { vertices, length } = this\n\t\tlet closestSegment = null\n\t\tlet closestDistance = Infinity\n\t\tlet distanceTraveled = 0\n\n\t\tfor (let i = 0; i < (this.isClosed ? vertices.length : vertices.length - 1); i++) {\n\t\t\tconst curr = vertices[i]\n\t\t\tconst next = vertices[(i + 1) % vertices.length]\n\n\t\t\tconst nearestPoint = Vec.NearestPointOnLineSegment(curr, next, point, true)\n\t\t\tconst distance = Vec.Dist(nearestPoint, point)\n\n\t\t\tif (distance < closestDistance) {\n\t\t\t\tclosestDistance = distance\n\t\t\t\tclosestSegment = {\n\t\t\t\t\tstart: curr,\n\t\t\t\t\tend: next,\n\t\t\t\t\tnearestPoint,\n\t\t\t\t\tdistanceToStart: distanceTraveled,\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tdistanceTraveled += Vec.Dist(curr, next)\n\t\t}\n\n\t\tassert(closestSegment)\n\n\t\tconst distanceAlongRoute =\n\t\t\tclosestSegment.distanceToStart + Vec.Dist(closestSegment.start, closestSegment.nearestPoint)\n\n\t\treturn distanceAlongRoute / length\n\t}\n\n\t/** @deprecated Iterate the vertices instead. */\n\tnearestPointOnLineSegment(A: VecLike, B: VecLike): Vec {\n\t\tconst { vertices } = this\n\t\tlet nearest: Vec | undefined\n\t\tlet dist = Infinity\n\t\tlet d: number, p: Vec, q: Vec\n\t\tfor (let i = 0; i < vertices.length; i++) {\n\t\t\tp = vertices[i]\n\t\t\tq = Vec.NearestPointOnLineSegment(A, B, p, true)\n\t\t\td = Vec.Dist2(p, q)\n\t\t\tif (d < dist) {\n\t\t\t\tdist = d\n\t\t\t\tnearest = q\n\t\t\t}\n\t\t}\n\t\tif (!nearest) throw Error('nearest point not found')\n\t\treturn nearest\n\t}\n\n\tisPointInBounds(point: VecLike, margin = 0) {\n\t\tconst { bounds } = this\n\t\treturn !(\n\t\t\tpoint.x < bounds.minX - margin ||\n\t\t\tpoint.y < bounds.minY - margin ||\n\t\t\tpoint.x > bounds.maxX + margin ||\n\t\t\tpoint.y > bounds.maxY + margin\n\t\t)\n\t}\n\n\ttransform(transform: MatModel, opts?: TransformedGeometry2dOptions): Geometry2d {\n\t\treturn new TransformedGeometry2d(this, transform, opts)\n\t}\n\n\tprivate _vertices: Vec[] | undefined\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget vertices(): Vec[] {\n\t\tif (!this._vertices) {\n\t\t\tthis._vertices = this.getVertices(Geometry2dFilters.EXCLUDE_LABELS)\n\t\t}\n\n\t\treturn this._vertices\n\t}\n\n\tgetBounds() {\n\t\treturn Box.FromPoints(this.vertices)\n\t}\n\n\tprivate _bounds: Box | undefined\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget bounds(): Box {\n\t\tif (!this._bounds) {\n\t\t\tthis._bounds = this.getBounds()\n\t\t}\n\t\treturn this._bounds\n\t}\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget center() {\n\t\treturn this.bounds.center\n\t}\n\n\tprivate _area: number | undefined\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget area() {\n\t\tif (!this._area) {\n\t\t\tthis._area = this.getArea()\n\t\t}\n\t\treturn this._area\n\t}\n\n\tgetArea() {\n\t\tif (!this.isClosed) {\n\t\t\treturn 0\n\t\t}\n\t\tconst { vertices } = this\n\t\tlet area = 0\n\t\tfor (let i = 0, n = vertices.length; i < n; i++) {\n\t\t\tconst curr = vertices[i]\n\t\t\tconst next = vertices[(i + 1) % n]\n\t\t\tarea += curr.x * next.y - next.x * curr.y\n\t\t}\n\t\treturn area / 2\n\t}\n\n\ttoSimpleSvgPath() {\n\t\tlet path = ''\n\n\t\tconst { vertices } = this\n\t\tconst n = vertices.length\n\n\t\tif (n === 0) return path\n\n\t\tpath += `M${vertices[0].x},${vertices[0].y}`\n\n\t\tfor (let i = 1; i < n; i++) {\n\t\t\tpath += `L${vertices[i].x},${vertices[i].y}`\n\t\t}\n\n\t\tif (this.isClosed) {\n\t\t\tpath += 'Z'\n\t\t}\n\n\t\treturn path\n\t}\n\n\tprivate _length?: number\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget length() {\n\t\tif (this._length) return this._length\n\t\tthis._length = this.getLength(Geometry2dFilters.EXCLUDE_LABELS)\n\t\treturn this._length\n\t}\n\n\tgetLength(_filters?: Geometry2dFilters) {\n\t\tconst vertices = this.getVertices(_filters ?? Geometry2dFilters.EXCLUDE_LABELS)\n\t\tif (vertices.length === 0) return 0\n\t\tlet prev = vertices[0]\n\t\tlet length = 0\n\t\tfor (let i = 1; i < vertices.length; i++) {\n\t\t\tconst next = vertices[i]\n\t\t\tlength += Vec.Dist(prev, next)\n\t\t\tprev = next\n\t\t}\n\t\tif (this.isClosed) {\n\t\t\tlength += Vec.Dist(vertices[vertices.length - 1], vertices[0])\n\t\t}\n\t\treturn length\n\t}\n\n\tabstract getSvgPathData(first: boolean): string\n}\n\n// =================================================================================================\n// Because Geometry2d.transform depends on TransformedGeometry2d, we need to define it here instead\n// of in its own files. This prevents a circular import error.\n// =================================================================================================\n\n/** @public */\nexport class TransformedGeometry2d extends Geometry2d {\n\tprivate readonly inverse: MatModel\n\tprivate readonly decomposed\n\n\tconstructor(\n\t\tprivate readonly geometry: Geometry2d,\n\t\tprivate readonly matrix: MatModel,\n\t\topts?: TransformedGeometry2dOptions\n\t) {\n\t\tsuper(geometry)\n\t\tthis.inverse = Mat.Inverse(matrix)\n\t\tthis.decomposed = Mat.Decompose(matrix)\n\n\t\tif (opts) {\n\t\t\tif (opts.isLabel != null) this.isLabel = opts.isLabel\n\t\t\tif (opts.isInternal != null) this.isInternal = opts.isInternal\n\t\t\tif (opts.debugColor != null) this.debugColor = opts.debugColor\n\t\t\tif (opts.ignore != null) this.ignore = opts.ignore\n\t\t}\n\n\t\tassert(\n\t\t\tapproximately(this.decomposed.scaleX, this.decomposed.scaleY),\n\t\t\t'non-uniform scaling is not yet supported'\n\t\t)\n\t}\n\n\tgetVertices(filters: Geometry2dFilters): Vec[] {\n\t\treturn this.geometry.getVertices(filters).map((v) => Mat.applyToPoint(this.matrix, v))\n\t}\n\n\tnearestPoint(point: VecLike, filters?: Geometry2dFilters): Vec {\n\t\treturn Mat.applyToPoint(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.nearestPoint(Mat.applyToPoint(this.inverse, point), filters)\n\t\t)\n\t}\n\n\toverride hitTestPoint(\n\t\tpoint: VecLike,\n\t\tmargin = 0,\n\t\thitInside?: boolean,\n\t\tfilters?: Geometry2dFilters\n\t): boolean {\n\t\treturn this.geometry.hitTestPoint(\n\t\t\tMat.applyToPoint(this.inverse, point),\n\t\t\tmargin / this.decomposed.scaleX,\n\t\t\thitInside,\n\t\t\tfilters\n\t\t)\n\t}\n\n\toverride distanceToPoint(point: VecLike, hitInside = false, filters?: Geometry2dFilters) {\n\t\treturn (\n\t\t\tthis.geometry.distanceToPoint(Mat.applyToPoint(this.inverse, point), hitInside, filters) *\n\t\t\tthis.decomposed.scaleX\n\t\t)\n\t}\n\n\toverride distanceToLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\treturn (\n\t\t\tthis.geometry.distanceToLineSegment(\n\t\t\t\tMat.applyToPoint(this.inverse, A),\n\t\t\t\tMat.applyToPoint(this.inverse, B),\n\t\t\t\tfilters\n\t\t\t) * this.decomposed.scaleX\n\t\t)\n\t}\n\n\toverride hitTestLineSegment(\n\t\tA: VecLike,\n\t\tB: VecLike,\n\t\tdistance = 0,\n\t\tfilters?: Geometry2dFilters\n\t): boolean {\n\t\treturn this.geometry.hitTestLineSegment(\n\t\t\tMat.applyToPoint(this.inverse, A),\n\t\t\tMat.applyToPoint(this.inverse, B),\n\t\t\tdistance / this.decomposed.scaleX,\n\t\t\tfilters\n\t\t)\n\t}\n\n\toverride intersectLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectLineSegment(\n\t\t\t\tMat.applyToPoint(this.inverse, A),\n\t\t\t\tMat.applyToPoint(this.inverse, B),\n\t\t\t\tfilters\n\t\t\t)\n\t\t)\n\t}\n\n\toverride intersectCircle(center: VecLike, radius: number, filters?: Geometry2dFilters) {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectCircle(\n\t\t\t\tMat.applyToPoint(this.inverse, center),\n\t\t\t\tradius / this.decomposed.scaleX,\n\t\t\t\tfilters\n\t\t\t)\n\t\t)\n\t}\n\n\toverride intersectPolygon(polygon: VecLike[], filters?: Geometry2dFilters): VecLike[] {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectPolygon(Mat.applyToPoints(this.inverse, polygon), filters)\n\t\t)\n\t}\n\n\toverride intersectPolyline(polyline: VecLike[], filters?: Geometry2dFilters): VecLike[] {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectPolyline(Mat.applyToPoints(this.inverse, polyline), filters)\n\t\t)\n\t}\n\n\toverride transform(transform: MatModel, opts?: TransformedGeometry2dOptions): Geometry2d {\n\t\treturn new TransformedGeometry2d(this.geometry, Mat.Multiply(transform, this.matrix), {\n\t\t\tisLabel: opts?.isLabel ?? this.isLabel,\n\t\t\tisInternal: opts?.isInternal ?? this.isInternal,\n\t\t\tdebugColor: opts?.debugColor ?? this.debugColor,\n\t\t\tignore: opts?.ignore ?? this.ignore,\n\t\t})\n\t}\n\n\tgetSvgPathData(): string {\n\t\tthrow new Error('Cannot get SVG path data for transformed geometry.')\n\t}\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import { assert, invLerp } from '@tldraw/utils'\nimport { Box } from '../Box'\nimport { Mat, MatModel } from '../Mat'\nimport { Vec, VecLike } from '../Vec'\nimport {\n\tintersectCirclePolygon,\n\tintersectCirclePolyline,\n\tintersectLineSegmentPolygon,\n\tintersectLineSegmentPolyline,\n\tintersectPolys,\n\tlinesIntersect,\n} from '../intersect'\nimport { approximately, pointInPolygon } from '../utils'\n\n/**\n * Filter geometry within a group.\n *\n * Filters are ignored when called directly on primitive geometries, but can be used to narrow down\n * the results of an operation on `Group2d` geometries.\n *\n * @public\n */\nexport interface Geometry2dFilters {\n\treadonly includeLabels?: boolean\n\treadonly includeInternal?: boolean\n}\n\n/** @public */\nexport const Geometry2dFilters: {\n\tEXCLUDE_NON_STANDARD: Geometry2dFilters\n\tINCLUDE_ALL: Geometry2dFilters\n\tEXCLUDE_LABELS: Geometry2dFilters\n\tEXCLUDE_INTERNAL: Geometry2dFilters\n} = {\n\tEXCLUDE_NON_STANDARD: {\n\t\tincludeLabels: false,\n\t\tincludeInternal: false,\n\t},\n\tINCLUDE_ALL: { includeLabels: true, includeInternal: true },\n\tEXCLUDE_LABELS: { includeLabels: false, includeInternal: true },\n\tEXCLUDE_INTERNAL: { includeLabels: true, includeInternal: false },\n}\n\n/** @public */\nexport interface TransformedGeometry2dOptions {\n\tisLabel?: boolean\n\tisInternal?: boolean\n\tdebugColor?: string\n\tignore?: boolean\n}\n\n/** @public */\nexport interface Geometry2dOptions extends TransformedGeometry2dOptions {\n\tisFilled: boolean\n\tisClosed: boolean\n}\n\n/** @public */\nexport abstract class Geometry2d {\n\tisFilled = false\n\tisClosed = true\n\tisLabel = false\n\tisInternal = false\n\tdebugColor?: string\n\tignore?: boolean\n\n\tconstructor(opts: Geometry2dOptions) {\n\t\tthis.isFilled = opts.isFilled\n\t\tthis.isClosed = opts.isClosed\n\t\tthis.isLabel = opts.isLabel ?? false\n\t\tthis.isInternal = opts.isInternal ?? false\n\t\tthis.debugColor = opts.debugColor\n\t\tthis.ignore = opts.ignore\n\t}\n\n\tisExcludedByFilter(filters?: Geometry2dFilters) {\n\t\tif (!filters) return false\n\t\tif (this.isLabel && !filters.includeLabels) return true\n\t\tif (this.isInternal && !filters.includeInternal) return true\n\t\treturn false\n\t}\n\n\tabstract getVertices(filters: Geometry2dFilters): Vec[]\n\n\tabstract nearestPoint(point: VecLike, _filters?: Geometry2dFilters): Vec\n\n\thitTestPoint(point: VecLike, margin = 0, hitInside = false, _filters?: Geometry2dFilters) {\n\t\t// First check whether the point is inside\n\t\tif (this.isClosed && (this.isFilled || hitInside) && pointInPolygon(point, this.vertices)) {\n\t\t\treturn true\n\t\t}\n\t\t// Then check whether the distance is within the margin\n\t\treturn Vec.Dist2(point, this.nearestPoint(point)) <= margin * margin\n\t}\n\n\tdistanceToPoint(point: VecLike, hitInside = false, filters?: Geometry2dFilters) {\n\t\treturn (\n\t\t\tVec.Dist(point, this.nearestPoint(point, filters)) *\n\t\t\t(this.isClosed && (this.isFilled || hitInside) && pointInPolygon(point, this.vertices)\n\t\t\t\t? -1\n\t\t\t\t: 1)\n\t\t)\n\t}\n\n\tdistanceToLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\tif (Vec.Equals(A, B)) return this.distanceToPoint(A, false, filters)\n\t\tconst { vertices } = this\n\t\tlet nearest: Vec | undefined\n\t\tlet dist = Infinity\n\t\tlet d: number, p: Vec, q: Vec\n\t\tconst nextLimit = this.isClosed ? vertices.length : vertices.length - 1\n\t\tfor (let i = 0; i < vertices.length; i++) {\n\t\t\tp = vertices[i]\n\t\t\tif (i < nextLimit) {\n\t\t\t\tconst next = vertices[(i + 1) % vertices.length]\n\t\t\t\tif (linesIntersect(A, B, p, next)) return 0\n\t\t\t}\n\t\t\tq = Vec.NearestPointOnLineSegment(A, B, p, true)\n\t\t\td = Vec.Dist2(p, q)\n\t\t\tif (d < dist) {\n\t\t\t\tdist = d\n\t\t\t\tnearest = q\n\t\t\t}\n\t\t}\n\t\tif (!nearest) throw Error('nearest point not found')\n\t\treturn this.isClosed && this.isFilled && pointInPolygon(nearest, this.vertices) ? -dist : dist\n\t}\n\n\thitTestLineSegment(A: VecLike, B: VecLike, distance = 0, filters?: Geometry2dFilters): boolean {\n\t\treturn this.distanceToLineSegment(A, B, filters) <= distance\n\t}\n\n\tintersectLineSegment(A: VecLike, B: VecLike, _filters?: Geometry2dFilters): VecLike[] {\n\t\tconst intersections = this.isClosed\n\t\t\t? intersectLineSegmentPolygon(A, B, this.vertices)\n\t\t\t: intersectLineSegmentPolyline(A, B, this.vertices)\n\n\t\treturn intersections ?? []\n\t}\n\n\tintersectCircle(center: VecLike, radius: number, _filters?: Geometry2dFilters): VecLike[] {\n\t\tconst intersections = this.isClosed\n\t\t\t? intersectCirclePolygon(center, radius, this.vertices)\n\t\t\t: intersectCirclePolyline(center, radius, this.vertices)\n\n\t\treturn intersections ?? []\n\t}\n\n\tintersectPolygon(polygon: VecLike[], _filters?: Geometry2dFilters): VecLike[] {\n\t\treturn intersectPolys(polygon, this.vertices, true, this.isClosed)\n\t}\n\n\tintersectPolyline(polyline: VecLike[], _filters?: Geometry2dFilters): VecLike[] {\n\t\treturn intersectPolys(polyline, this.vertices, false, this.isClosed)\n\t}\n\n\t/**\n\t * Find a point along the edge of the geometry that is a fraction `t` along the entire way round.\n\t */\n\tinterpolateAlongEdge(t: number, _filters?: Geometry2dFilters): Vec {\n\t\tconst { vertices } = this\n\n\t\tif (t <= 0) return vertices[0]\n\n\t\tconst distanceToTravel = t * this.length\n\t\tlet distanceTraveled = 0\n\n\t\tfor (let i = 0; i < (this.isClosed ? vertices.length : vertices.length - 1); i++) {\n\t\t\tconst curr = vertices[i]\n\t\t\tconst next = vertices[(i + 1) % vertices.length]\n\t\t\tconst dist = Vec.Dist(curr, next)\n\t\t\tconst newDistanceTraveled = distanceTraveled + dist\n\t\t\tif (newDistanceTraveled >= distanceToTravel) {\n\t\t\t\tconst p = Vec.Lrp(\n\t\t\t\t\tcurr,\n\t\t\t\t\tnext,\n\t\t\t\t\tinvLerp(distanceTraveled, newDistanceTraveled, distanceToTravel)\n\t\t\t\t)\n\t\t\t\treturn p\n\t\t\t}\n\t\t\tdistanceTraveled = newDistanceTraveled\n\t\t}\n\n\t\treturn this.isClosed ? vertices[0] : vertices[vertices.length - 1]\n\t}\n\n\t/**\n\t * Take `point`, find the closest point to it on the edge of the geometry, and return how far\n\t * along the edge it is as a fraction of the total length.\n\t */\n\tuninterpolateAlongEdge(point: VecLike, _filters?: Geometry2dFilters): number {\n\t\tconst { vertices, length } = this\n\t\tlet closestSegment = null\n\t\tlet closestDistance = Infinity\n\t\tlet distanceTraveled = 0\n\n\t\tfor (let i = 0; i < (this.isClosed ? vertices.length : vertices.length - 1); i++) {\n\t\t\tconst curr = vertices[i]\n\t\t\tconst next = vertices[(i + 1) % vertices.length]\n\n\t\t\tconst nearestPoint = Vec.NearestPointOnLineSegment(curr, next, point, true)\n\t\t\tconst distance = Vec.Dist(nearestPoint, point)\n\n\t\t\tif (distance < closestDistance) {\n\t\t\t\tclosestDistance = distance\n\t\t\t\tclosestSegment = {\n\t\t\t\t\tstart: curr,\n\t\t\t\t\tend: next,\n\t\t\t\t\tnearestPoint,\n\t\t\t\t\tdistanceToStart: distanceTraveled,\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tdistanceTraveled += Vec.Dist(curr, next)\n\t\t}\n\n\t\tassert(closestSegment)\n\n\t\tconst distanceAlongRoute =\n\t\t\tclosestSegment.distanceToStart + Vec.Dist(closestSegment.start, closestSegment.nearestPoint)\n\n\t\treturn distanceAlongRoute / length\n\t}\n\n\t/** @deprecated Iterate the vertices instead. */\n\tnearestPointOnLineSegment(A: VecLike, B: VecLike): Vec {\n\t\tconst { vertices } = this\n\t\tlet nearest: Vec | undefined\n\t\tlet dist = Infinity\n\t\tlet d: number, p: Vec, q: Vec\n\t\tfor (let i = 0; i < vertices.length; i++) {\n\t\t\tp = vertices[i]\n\t\t\tq = Vec.NearestPointOnLineSegment(A, B, p, true)\n\t\t\td = Vec.Dist2(p, q)\n\t\t\tif (d < dist) {\n\t\t\t\tdist = d\n\t\t\t\tnearest = q\n\t\t\t}\n\t\t}\n\t\tif (!nearest) throw Error('nearest point not found')\n\t\treturn nearest\n\t}\n\n\tisPointInBounds(point: VecLike, margin = 0) {\n\t\tconst { bounds } = this\n\t\treturn !(\n\t\t\tpoint.x < bounds.minX - margin ||\n\t\t\tpoint.y < bounds.minY - margin ||\n\t\t\tpoint.x > bounds.maxX + margin ||\n\t\t\tpoint.y > bounds.maxY + margin\n\t\t)\n\t}\n\n\ttransform(transform: MatModel, opts?: TransformedGeometry2dOptions): Geometry2d {\n\t\treturn new TransformedGeometry2d(this, transform, opts)\n\t}\n\n\tprivate _vertices: Vec[] | undefined\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget vertices(): Vec[] {\n\t\tif (!this._vertices) {\n\t\t\tthis._vertices = this.getVertices(Geometry2dFilters.EXCLUDE_LABELS)\n\t\t}\n\n\t\treturn this._vertices\n\t}\n\n\tgetBounds() {\n\t\treturn Box.FromPoints(this.vertices)\n\t}\n\n\tprivate _bounds: Box | undefined\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget bounds(): Box {\n\t\tif (!this._bounds) {\n\t\t\tthis._bounds = this.getBounds()\n\t\t}\n\t\treturn this._bounds\n\t}\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget center() {\n\t\treturn this.bounds.center\n\t}\n\n\tprivate _area: number | undefined\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget area() {\n\t\tif (!this._area) {\n\t\t\tthis._area = this.getArea()\n\t\t}\n\t\treturn this._area\n\t}\n\n\tgetArea() {\n\t\tif (!this.isClosed) {\n\t\t\treturn 0\n\t\t}\n\t\tconst { vertices } = this\n\t\tlet area = 0\n\t\tfor (let i = 0, n = vertices.length; i < n; i++) {\n\t\t\tconst curr = vertices[i]\n\t\t\tconst next = vertices[(i + 1) % n]\n\t\t\tarea += curr.x * next.y - next.x * curr.y\n\t\t}\n\t\treturn area / 2\n\t}\n\n\ttoSimpleSvgPath() {\n\t\tlet path = ''\n\n\t\tconst { vertices } = this\n\t\tconst n = vertices.length\n\n\t\tif (n === 0) return path\n\n\t\tpath += `M${vertices[0].x},${vertices[0].y}`\n\n\t\tfor (let i = 1; i < n; i++) {\n\t\t\tpath += `L${vertices[i].x},${vertices[i].y}`\n\t\t}\n\n\t\tif (this.isClosed) {\n\t\t\tpath += 'Z'\n\t\t}\n\n\t\treturn path\n\t}\n\n\tprivate _length?: number\n\n\t// eslint-disable-next-line no-restricted-syntax\n\tget length() {\n\t\tif (this._length) return this._length\n\t\tthis._length = this.getLength(Geometry2dFilters.EXCLUDE_LABELS)\n\t\treturn this._length\n\t}\n\n\tgetLength(_filters?: Geometry2dFilters) {\n\t\tconst vertices = this.getVertices(_filters ?? Geometry2dFilters.EXCLUDE_LABELS)\n\t\tif (vertices.length === 0) return 0\n\t\tlet prev = vertices[0]\n\t\tlet length = 0\n\t\tfor (let i = 1; i < vertices.length; i++) {\n\t\t\tconst next = vertices[i]\n\t\t\tlength += Vec.Dist(prev, next)\n\t\t\tprev = next\n\t\t}\n\t\tif (this.isClosed) {\n\t\t\tlength += Vec.Dist(vertices[vertices.length - 1], vertices[0])\n\t\t}\n\t\treturn length\n\t}\n\n\tabstract getSvgPathData(first: boolean): string\n}\n\n// =================================================================================================\n// Because Geometry2d.transform depends on TransformedGeometry2d, we need to define it here instead\n// of in its own files. This prevents a circular import error.\n// =================================================================================================\n\n/** @public */\nexport class TransformedGeometry2d extends Geometry2d {\n\tprivate readonly inverse: MatModel\n\tprivate readonly decomposed\n\n\tconstructor(\n\t\tprivate readonly geometry: Geometry2d,\n\t\tprivate readonly matrix: MatModel,\n\t\topts?: TransformedGeometry2dOptions\n\t) {\n\t\tsuper(geometry)\n\t\tthis.inverse = Mat.Inverse(matrix)\n\t\tthis.decomposed = Mat.Decompose(matrix)\n\n\t\tif (opts) {\n\t\t\tif (opts.isLabel != null) this.isLabel = opts.isLabel\n\t\t\tif (opts.isInternal != null) this.isInternal = opts.isInternal\n\t\t\tif (opts.debugColor != null) this.debugColor = opts.debugColor\n\t\t\tif (opts.ignore != null) this.ignore = opts.ignore\n\t\t}\n\n\t\tassert(\n\t\t\tapproximately(this.decomposed.scaleX, this.decomposed.scaleY),\n\t\t\t'non-uniform scaling is not yet supported'\n\t\t)\n\t}\n\n\tgetVertices(filters: Geometry2dFilters): Vec[] {\n\t\treturn this.geometry.getVertices(filters).map((v) => Mat.applyToPoint(this.matrix, v))\n\t}\n\n\tnearestPoint(point: VecLike, filters?: Geometry2dFilters): Vec {\n\t\treturn Mat.applyToPoint(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.nearestPoint(Mat.applyToPoint(this.inverse, point), filters)\n\t\t)\n\t}\n\n\toverride hitTestPoint(\n\t\tpoint: VecLike,\n\t\tmargin = 0,\n\t\thitInside?: boolean,\n\t\tfilters?: Geometry2dFilters\n\t): boolean {\n\t\treturn this.geometry.hitTestPoint(\n\t\t\tMat.applyToPoint(this.inverse, point),\n\t\t\tmargin / this.decomposed.scaleX,\n\t\t\thitInside,\n\t\t\tfilters\n\t\t)\n\t}\n\n\toverride distanceToPoint(point: VecLike, hitInside = false, filters?: Geometry2dFilters) {\n\t\treturn (\n\t\t\tthis.geometry.distanceToPoint(Mat.applyToPoint(this.inverse, point), hitInside, filters) *\n\t\t\tthis.decomposed.scaleX\n\t\t)\n\t}\n\n\toverride distanceToLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\treturn (\n\t\t\tthis.geometry.distanceToLineSegment(\n\t\t\t\tMat.applyToPoint(this.inverse, A),\n\t\t\t\tMat.applyToPoint(this.inverse, B),\n\t\t\t\tfilters\n\t\t\t) * this.decomposed.scaleX\n\t\t)\n\t}\n\n\toverride hitTestLineSegment(\n\t\tA: VecLike,\n\t\tB: VecLike,\n\t\tdistance = 0,\n\t\tfilters?: Geometry2dFilters\n\t): boolean {\n\t\treturn this.geometry.hitTestLineSegment(\n\t\t\tMat.applyToPoint(this.inverse, A),\n\t\t\tMat.applyToPoint(this.inverse, B),\n\t\t\tdistance / this.decomposed.scaleX,\n\t\t\tfilters\n\t\t)\n\t}\n\n\toverride intersectLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectLineSegment(\n\t\t\t\tMat.applyToPoint(this.inverse, A),\n\t\t\t\tMat.applyToPoint(this.inverse, B),\n\t\t\t\tfilters\n\t\t\t)\n\t\t)\n\t}\n\n\toverride intersectCircle(center: VecLike, radius: number, filters?: Geometry2dFilters) {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectCircle(\n\t\t\t\tMat.applyToPoint(this.inverse, center),\n\t\t\t\tradius / this.decomposed.scaleX,\n\t\t\t\tfilters\n\t\t\t)\n\t\t)\n\t}\n\n\toverride intersectPolygon(polygon: VecLike[], filters?: Geometry2dFilters): VecLike[] {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectPolygon(Mat.applyToPoints(this.inverse, polygon), filters)\n\t\t)\n\t}\n\n\toverride intersectPolyline(polyline: VecLike[], filters?: Geometry2dFilters): VecLike[] {\n\t\treturn Mat.applyToPoints(\n\t\t\tthis.matrix,\n\t\t\tthis.geometry.intersectPolyline(Mat.applyToPoints(this.inverse, polyline), filters)\n\t\t)\n\t}\n\n\toverride transform(transform: MatModel, opts?: TransformedGeometry2dOptions): Geometry2d {\n\t\treturn new TransformedGeometry2d(this.geometry, Mat.Multiply(transform, this.matrix), {\n\t\t\tisLabel: opts?.isLabel ?? this.isLabel,\n\t\t\tisInternal: opts?.isInternal ?? this.isInternal,\n\t\t\tdebugColor: opts?.debugColor ?? this.debugColor,\n\t\t\tignore: opts?.ignore ?? this.ignore,\n\t\t})\n\t}\n\n\tgetSvgPathData(): string {\n\t\tthrow new Error('Cannot get SVG path data for transformed geometry.')\n\t}\n}\n"],
5
+ "mappings": "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",
6
6
  "names": ["import_utils"]
7
7
  }
@@ -31,18 +31,13 @@ class Group2d extends import_Geometry2d.Geometry2d {
31
31
  ignoredChildren = [];
32
32
  constructor(config) {
33
33
  super({ ...config, isClosed: true, isFilled: false });
34
- const addChildren = (children) => {
35
- for (const child of children) {
36
- if (child instanceof Group2d) {
37
- addChildren(child.children);
38
- } else if (child.ignore) {
39
- this.ignoredChildren.push(child);
40
- } else {
41
- this.children.push(child);
42
- }
34
+ for (const child of config.children) {
35
+ if (child.ignore) {
36
+ this.ignoredChildren.push(child);
37
+ } else {
38
+ this.children.push(child);
43
39
  }
44
- };
45
- addChildren(config.children);
40
+ }
46
41
  if (this.children.length === 0) throw Error("Group2d must have at least one child");
47
42
  }
48
43
  getVertices(filters) {
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../../src/lib/primitives/geometry/Group2d.ts"],
4
- "sourcesContent": ["import { EMPTY_ARRAY } from '@tldraw/state'\nimport { assert, invLerp, lerp } from '@tldraw/utils'\nimport { Box } from '../Box'\nimport { Mat } from '../Mat'\nimport { Vec, VecLike } from '../Vec'\nimport { Geometry2d, Geometry2dFilters, Geometry2dOptions } from './Geometry2d'\n\n/** @public */\nexport class Group2d extends Geometry2d {\n\tchildren: Geometry2d[] = []\n\tignoredChildren: Geometry2d[] = []\n\n\tconstructor(\n\t\tconfig: Omit<Geometry2dOptions, 'isClosed' | 'isFilled'> & {\n\t\t\tchildren: Geometry2d[]\n\t\t}\n\t) {\n\t\tsuper({ ...config, isClosed: true, isFilled: false })\n\n\t\tconst addChildren = (children: Geometry2d[]) => {\n\t\t\tfor (const child of children) {\n\t\t\t\tif (child instanceof Group2d) {\n\t\t\t\t\taddChildren(child.children)\n\t\t\t\t} else if (child.ignore) {\n\t\t\t\t\tthis.ignoredChildren.push(child)\n\t\t\t\t} else {\n\t\t\t\t\tthis.children.push(child)\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\taddChildren(config.children)\n\n\t\tif (this.children.length === 0) throw Error('Group2d must have at least one child')\n\t}\n\n\toverride getVertices(filters: Geometry2dFilters): Vec[] {\n\t\tif (this.isExcludedByFilter(filters)) return []\n\t\treturn this.children\n\t\t\t.filter((c) => !c.isExcludedByFilter(filters))\n\t\t\t.flatMap((c) => c.getVertices(filters))\n\t}\n\n\toverride nearestPoint(point: VecLike, filters?: Geometry2dFilters): Vec {\n\t\tlet dist = Infinity\n\t\tlet nearest: Vec | undefined\n\n\t\tconst { children } = this\n\n\t\tif (children.length === 0) {\n\t\t\tthrow Error('no children')\n\t\t}\n\n\t\tlet p: Vec\n\t\tlet d: number\n\t\tfor (const child of children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tp = child.nearestPoint(point, filters)\n\t\t\td = Vec.Dist2(p, point)\n\t\t\tif (d < dist) {\n\t\t\t\tdist = d\n\t\t\t\tnearest = p\n\t\t\t}\n\t\t}\n\t\tif (!nearest) throw Error('nearest point not found')\n\t\treturn nearest\n\t}\n\n\toverride distanceToPoint(point: VecLike, hitInside = false, filters?: Geometry2dFilters) {\n\t\tlet smallestDistance = Infinity\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tconst distance = child.distanceToPoint(point, hitInside, filters)\n\t\t\tif (distance < smallestDistance) {\n\t\t\t\tsmallestDistance = distance\n\t\t\t}\n\t\t}\n\t\treturn smallestDistance\n\t}\n\n\toverride hitTestPoint(\n\t\tpoint: VecLike,\n\t\tmargin: number,\n\t\thitInside: boolean,\n\t\tfilters = Geometry2dFilters.EXCLUDE_LABELS\n\t): boolean {\n\t\treturn !!this.children\n\t\t\t.filter((c) => !c.isExcludedByFilter(filters))\n\t\t\t.find((c) => c.hitTestPoint(point, margin, hitInside))\n\t}\n\n\toverride hitTestLineSegment(\n\t\tA: VecLike,\n\t\tB: VecLike,\n\t\tzoom: number,\n\t\tfilters = Geometry2dFilters.EXCLUDE_LABELS\n\t): boolean {\n\t\treturn !!this.children\n\t\t\t.filter((c) => !c.isExcludedByFilter(filters))\n\t\t\t.find((c) => c.hitTestLineSegment(A, B, zoom))\n\t}\n\n\toverride intersectLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectLineSegment(A, B, filters)\n\t\t})\n\t}\n\n\toverride intersectCircle(center: VecLike, radius: number, filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectCircle(center, radius, filters)\n\t\t})\n\t}\n\n\toverride intersectPolygon(polygon: VecLike[], filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectPolygon(polygon, filters)\n\t\t})\n\t}\n\n\toverride intersectPolyline(polyline: VecLike[], filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectPolyline(polyline, filters)\n\t\t})\n\t}\n\n\toverride interpolateAlongEdge(t: number, filters?: Geometry2dFilters): Vec {\n\t\tconst totalLength = this.getLength(filters)\n\n\t\tconst distanceToTravel = t * totalLength\n\t\tlet distanceTraveled = 0\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tconst childLength = child.length\n\t\t\tconst newDistanceTraveled = distanceTraveled + childLength\n\t\t\tif (newDistanceTraveled >= distanceToTravel) {\n\t\t\t\treturn child.interpolateAlongEdge(\n\t\t\t\t\tinvLerp(distanceTraveled, newDistanceTraveled, distanceToTravel),\n\t\t\t\t\tfilters\n\t\t\t\t)\n\t\t\t}\n\t\t\tdistanceTraveled = newDistanceTraveled\n\t\t}\n\n\t\treturn this.children[this.children.length - 1].interpolateAlongEdge(1, filters)\n\t}\n\n\toverride uninterpolateAlongEdge(point: VecLike, filters?: Geometry2dFilters): number {\n\t\tconst totalLength = this.getLength(filters)\n\n\t\tlet closestChild = null\n\t\tlet closestDistance = Infinity\n\t\tlet distanceTraveled = 0\n\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tconst childLength = child.getLength(filters)\n\t\t\tconst newDistanceTraveled = distanceTraveled + childLength\n\n\t\t\tconst distance = child.distanceToPoint(point, false, filters)\n\t\t\tif (distance < closestDistance) {\n\t\t\t\tclosestDistance = distance\n\t\t\t\tclosestChild = {\n\t\t\t\t\tstartLength: distanceTraveled,\n\t\t\t\t\tendLength: newDistanceTraveled,\n\t\t\t\t\tchild,\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tdistanceTraveled = newDistanceTraveled\n\t\t}\n\n\t\tassert(closestChild)\n\n\t\tconst normalizedDistanceInChild = closestChild.child.uninterpolateAlongEdge(point, filters)\n\t\tconst childTLength = lerp(\n\t\t\tclosestChild.startLength,\n\t\t\tclosestChild.endLength,\n\t\t\tnormalizedDistanceInChild\n\t\t)\n\t\treturn childTLength / totalLength\n\t}\n\n\toverride transform(transform: Mat): Geometry2d {\n\t\treturn new Group2d({\n\t\t\tchildren: this.children.map((c) => c.transform(transform)),\n\t\t\tisLabel: this.isLabel,\n\t\t\tdebugColor: this.debugColor,\n\t\t\tignore: this.ignore,\n\t\t})\n\t}\n\n\tgetArea() {\n\t\t// todo: this is a temporary solution, assuming that the first child defines the group size; we would want to flatten the group and then find the area of the hull polygon\n\t\treturn this.children[0].area\n\t}\n\n\ttoSimpleSvgPath() {\n\t\tlet path = ''\n\t\tfor (const child of this.children) {\n\t\t\tpath += child.toSimpleSvgPath()\n\t\t}\n\n\t\tconst corners = Box.FromPoints(this.vertices).corners\n\t\t// draw just a few pixels around each corner, e.g. an L shape for the bottom left\n\n\t\tfor (let i = 0, n = corners.length; i < n; i++) {\n\t\t\tconst corner = corners[i]\n\t\t\tconst prevCorner = corners[(i - 1 + n) % n]\n\t\t\tconst prevDist = corner.dist(prevCorner)\n\t\t\tconst nextCorner = corners[(i + 1) % n]\n\t\t\tconst nextDist = corner.dist(nextCorner)\n\n\t\t\tconst A = corner.clone().lrp(prevCorner, 4 / prevDist)\n\t\t\tconst B = corner\n\t\t\tconst C = corner.clone().lrp(nextCorner, 4 / nextDist)\n\n\t\t\tpath += `M${A.x},${A.y} L${B.x},${B.y} L${C.x},${C.y} `\n\t\t}\n\t\treturn path\n\t}\n\n\tgetLength(filters?: Geometry2dFilters): number {\n\t\tlet length = 0\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tlength += child.length\n\t\t}\n\t\treturn length\n\t}\n\n\tgetSvgPathData(): string {\n\t\treturn this.children.map((c, i) => (c.isLabel ? '' : c.getSvgPathData(i === 0))).join(' ')\n\t}\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import { EMPTY_ARRAY } from '@tldraw/state'\nimport { assert, invLerp, lerp } from '@tldraw/utils'\nimport { Box } from '../Box'\nimport { Mat } from '../Mat'\nimport { Vec, VecLike } from '../Vec'\nimport { Geometry2d, Geometry2dFilters, Geometry2dOptions } from './Geometry2d'\n\n/** @public */\nexport class Group2d extends Geometry2d {\n\tchildren: Geometry2d[] = []\n\tignoredChildren: Geometry2d[] = []\n\n\tconstructor(\n\t\tconfig: Omit<Geometry2dOptions, 'isClosed' | 'isFilled'> & {\n\t\t\tchildren: Geometry2d[]\n\t\t}\n\t) {\n\t\tsuper({ ...config, isClosed: true, isFilled: false })\n\n\t\tfor (const child of config.children) {\n\t\t\tif (child.ignore) {\n\t\t\t\tthis.ignoredChildren.push(child)\n\t\t\t} else {\n\t\t\t\tthis.children.push(child)\n\t\t\t}\n\t\t}\n\n\t\tif (this.children.length === 0) throw Error('Group2d must have at least one child')\n\t}\n\n\toverride getVertices(filters: Geometry2dFilters): Vec[] {\n\t\tif (this.isExcludedByFilter(filters)) return []\n\t\treturn this.children\n\t\t\t.filter((c) => !c.isExcludedByFilter(filters))\n\t\t\t.flatMap((c) => c.getVertices(filters))\n\t}\n\n\toverride nearestPoint(point: VecLike, filters?: Geometry2dFilters): Vec {\n\t\tlet dist = Infinity\n\t\tlet nearest: Vec | undefined\n\n\t\tconst { children } = this\n\n\t\tif (children.length === 0) {\n\t\t\tthrow Error('no children')\n\t\t}\n\n\t\tlet p: Vec\n\t\tlet d: number\n\t\tfor (const child of children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tp = child.nearestPoint(point, filters)\n\t\t\td = Vec.Dist2(p, point)\n\t\t\tif (d < dist) {\n\t\t\t\tdist = d\n\t\t\t\tnearest = p\n\t\t\t}\n\t\t}\n\t\tif (!nearest) throw Error('nearest point not found')\n\t\treturn nearest\n\t}\n\n\toverride distanceToPoint(point: VecLike, hitInside = false, filters?: Geometry2dFilters) {\n\t\tlet smallestDistance = Infinity\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tconst distance = child.distanceToPoint(point, hitInside, filters)\n\t\t\tif (distance < smallestDistance) {\n\t\t\t\tsmallestDistance = distance\n\t\t\t}\n\t\t}\n\t\treturn smallestDistance\n\t}\n\n\toverride hitTestPoint(\n\t\tpoint: VecLike,\n\t\tmargin: number,\n\t\thitInside: boolean,\n\t\tfilters = Geometry2dFilters.EXCLUDE_LABELS\n\t): boolean {\n\t\treturn !!this.children\n\t\t\t.filter((c) => !c.isExcludedByFilter(filters))\n\t\t\t.find((c) => c.hitTestPoint(point, margin, hitInside))\n\t}\n\n\toverride hitTestLineSegment(\n\t\tA: VecLike,\n\t\tB: VecLike,\n\t\tzoom: number,\n\t\tfilters = Geometry2dFilters.EXCLUDE_LABELS\n\t): boolean {\n\t\treturn !!this.children\n\t\t\t.filter((c) => !c.isExcludedByFilter(filters))\n\t\t\t.find((c) => c.hitTestLineSegment(A, B, zoom))\n\t}\n\n\toverride intersectLineSegment(A: VecLike, B: VecLike, filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectLineSegment(A, B, filters)\n\t\t})\n\t}\n\n\toverride intersectCircle(center: VecLike, radius: number, filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectCircle(center, radius, filters)\n\t\t})\n\t}\n\n\toverride intersectPolygon(polygon: VecLike[], filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectPolygon(polygon, filters)\n\t\t})\n\t}\n\n\toverride intersectPolyline(polyline: VecLike[], filters?: Geometry2dFilters) {\n\t\treturn this.children.flatMap((child) => {\n\t\t\tif (child.isExcludedByFilter(filters)) return EMPTY_ARRAY\n\t\t\treturn child.intersectPolyline(polyline, filters)\n\t\t})\n\t}\n\n\toverride interpolateAlongEdge(t: number, filters?: Geometry2dFilters): Vec {\n\t\tconst totalLength = this.getLength(filters)\n\n\t\tconst distanceToTravel = t * totalLength\n\t\tlet distanceTraveled = 0\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tconst childLength = child.length\n\t\t\tconst newDistanceTraveled = distanceTraveled + childLength\n\t\t\tif (newDistanceTraveled >= distanceToTravel) {\n\t\t\t\treturn child.interpolateAlongEdge(\n\t\t\t\t\tinvLerp(distanceTraveled, newDistanceTraveled, distanceToTravel),\n\t\t\t\t\tfilters\n\t\t\t\t)\n\t\t\t}\n\t\t\tdistanceTraveled = newDistanceTraveled\n\t\t}\n\n\t\treturn this.children[this.children.length - 1].interpolateAlongEdge(1, filters)\n\t}\n\n\toverride uninterpolateAlongEdge(point: VecLike, filters?: Geometry2dFilters): number {\n\t\tconst totalLength = this.getLength(filters)\n\n\t\tlet closestChild = null\n\t\tlet closestDistance = Infinity\n\t\tlet distanceTraveled = 0\n\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tconst childLength = child.getLength(filters)\n\t\t\tconst newDistanceTraveled = distanceTraveled + childLength\n\n\t\t\tconst distance = child.distanceToPoint(point, false, filters)\n\t\t\tif (distance < closestDistance) {\n\t\t\t\tclosestDistance = distance\n\t\t\t\tclosestChild = {\n\t\t\t\t\tstartLength: distanceTraveled,\n\t\t\t\t\tendLength: newDistanceTraveled,\n\t\t\t\t\tchild,\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tdistanceTraveled = newDistanceTraveled\n\t\t}\n\n\t\tassert(closestChild)\n\n\t\tconst normalizedDistanceInChild = closestChild.child.uninterpolateAlongEdge(point, filters)\n\t\tconst childTLength = lerp(\n\t\t\tclosestChild.startLength,\n\t\t\tclosestChild.endLength,\n\t\t\tnormalizedDistanceInChild\n\t\t)\n\t\treturn childTLength / totalLength\n\t}\n\n\toverride transform(transform: Mat): Geometry2d {\n\t\treturn new Group2d({\n\t\t\tchildren: this.children.map((c) => c.transform(transform)),\n\t\t\tisLabel: this.isLabel,\n\t\t\tdebugColor: this.debugColor,\n\t\t\tignore: this.ignore,\n\t\t})\n\t}\n\n\tgetArea() {\n\t\t// todo: this is a temporary solution, assuming that the first child defines the group size; we would want to flatten the group and then find the area of the hull polygon\n\t\treturn this.children[0].area\n\t}\n\n\ttoSimpleSvgPath() {\n\t\tlet path = ''\n\t\tfor (const child of this.children) {\n\t\t\tpath += child.toSimpleSvgPath()\n\t\t}\n\n\t\tconst corners = Box.FromPoints(this.vertices).corners\n\t\t// draw just a few pixels around each corner, e.g. an L shape for the bottom left\n\n\t\tfor (let i = 0, n = corners.length; i < n; i++) {\n\t\t\tconst corner = corners[i]\n\t\t\tconst prevCorner = corners[(i - 1 + n) % n]\n\t\t\tconst prevDist = corner.dist(prevCorner)\n\t\t\tconst nextCorner = corners[(i + 1) % n]\n\t\t\tconst nextDist = corner.dist(nextCorner)\n\n\t\t\tconst A = corner.clone().lrp(prevCorner, 4 / prevDist)\n\t\t\tconst B = corner\n\t\t\tconst C = corner.clone().lrp(nextCorner, 4 / nextDist)\n\n\t\t\tpath += `M${A.x},${A.y} L${B.x},${B.y} L${C.x},${C.y} `\n\t\t}\n\t\treturn path\n\t}\n\n\tgetLength(filters?: Geometry2dFilters): number {\n\t\tlet length = 0\n\t\tfor (const child of this.children) {\n\t\t\tif (child.isExcludedByFilter(filters)) continue\n\t\t\tlength += child.length\n\t\t}\n\t\treturn length\n\t}\n\n\tgetSvgPathData(): string {\n\t\treturn this.children.map((c, i) => (c.isLabel ? '' : c.getSvgPathData(i === 0))).join(' ')\n\t}\n}\n"],
5
+ "mappings": "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",
6
6
  "names": []
7
7
  }
@@ -29,7 +29,7 @@ __export(dom_exports, {
29
29
  module.exports = __toCommonJS(dom_exports);
30
30
  var import_debug_flags = require("./debug-flags");
31
31
  function loopToHtmlElement(elm) {
32
- if (elm.nodeType === Node.ELEMENT_NODE) return elm;
32
+ if (elm instanceof HTMLElement) return elm;
33
33
  if (elm.parentElement) return loopToHtmlElement(elm.parentElement);
34
34
  else throw Error("Could not find a parent element of an HTML type!");
35
35
  }