tldraw 3.16.0-canary.aceca4c951a7 → 3.16.0-canary.c1bcdabc9513
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist-cjs/index.d.ts +73 -0
- package/dist-cjs/index.js +5 -1
- package/dist-cjs/index.js.map +2 -2
- package/dist-cjs/lib/shapes/shared/ShapeFill.js +1 -1
- package/dist-cjs/lib/shapes/shared/ShapeFill.js.map +2 -2
- package/dist-cjs/lib/shapes/shared/freehand/svg.js.map +2 -2
- package/dist-cjs/lib/tools/EraserTool/childStates/Erasing.js +25 -1
- package/dist-cjs/lib/tools/EraserTool/childStates/Erasing.js.map +2 -2
- package/dist-cjs/lib/tools/EraserTool/childStates/Pointing.js +12 -0
- package/dist-cjs/lib/tools/EraserTool/childStates/Pointing.js.map +2 -2
- package/dist-cjs/lib/ui/components/primitives/TldrawUiTooltip.js +25 -10
- package/dist-cjs/lib/ui/components/primitives/TldrawUiTooltip.js.map +2 -2
- package/dist-cjs/lib/ui/components/primitives/menus/TldrawUiMenuItem.js +2 -1
- package/dist-cjs/lib/ui/components/primitives/menus/TldrawUiMenuItem.js.map +2 -2
- package/dist-cjs/lib/ui/hooks/useTools.js +5 -5
- package/dist-cjs/lib/ui/hooks/useTools.js.map +2 -2
- package/dist-cjs/lib/ui/version.js +3 -3
- package/dist-cjs/lib/ui/version.js.map +1 -1
- package/dist-esm/index.d.mts +73 -0
- package/dist-esm/index.mjs +5 -1
- package/dist-esm/index.mjs.map +2 -2
- package/dist-esm/lib/shapes/shared/ShapeFill.mjs +1 -1
- package/dist-esm/lib/shapes/shared/ShapeFill.mjs.map +2 -2
- package/dist-esm/lib/shapes/shared/freehand/svg.mjs.map +2 -2
- package/dist-esm/lib/tools/EraserTool/childStates/Erasing.mjs +26 -1
- package/dist-esm/lib/tools/EraserTool/childStates/Erasing.mjs.map +2 -2
- package/dist-esm/lib/tools/EraserTool/childStates/Pointing.mjs +13 -0
- package/dist-esm/lib/tools/EraserTool/childStates/Pointing.mjs.map +2 -2
- package/dist-esm/lib/ui/components/primitives/TldrawUiTooltip.mjs +25 -10
- package/dist-esm/lib/ui/components/primitives/TldrawUiTooltip.mjs.map +2 -2
- package/dist-esm/lib/ui/components/primitives/menus/TldrawUiMenuItem.mjs +2 -1
- package/dist-esm/lib/ui/components/primitives/menus/TldrawUiMenuItem.mjs.map +2 -2
- package/dist-esm/lib/ui/hooks/useTools.mjs +5 -5
- package/dist-esm/lib/ui/hooks/useTools.mjs.map +2 -2
- package/dist-esm/lib/ui/version.mjs +3 -3
- package/dist-esm/lib/ui/version.mjs.map +1 -1
- package/package.json +11 -34
- package/src/index.ts +3 -0
- package/src/lib/shapes/arrow/ArrowShapeOptions.test.ts +2 -1
- package/src/lib/shapes/arrow/ArrowShapeTool.test.ts +4 -3
- package/src/lib/shapes/arrow/ArrowShapeUtil.test.ts +7 -6
- package/src/lib/shapes/draw/DrawShapeTool.test.ts +0 -5
- package/src/lib/shapes/line/LineShapeUtil.test.tsx +4 -3
- package/src/lib/shapes/line/__snapshots__/LineShapeUtil.test.tsx.snap +2 -2
- package/src/lib/shapes/shared/ShapeFill.tsx +1 -1
- package/src/lib/shapes/shared/freehand/svg.ts +2 -0
- package/src/lib/shapes/text/TextShapeTool.test.ts +6 -5
- package/src/lib/tools/EraserTool/childStates/Erasing.ts +34 -1
- package/src/lib/tools/EraserTool/childStates/Pointing.ts +20 -0
- package/src/lib/ui/components/primitives/TldrawUiTooltip.tsx +36 -10
- package/src/lib/ui/components/primitives/menus/TldrawUiMenuItem.tsx +3 -2
- package/src/lib/ui/hooks/useTools.tsx +7 -5
- package/src/lib/ui/version.ts +3 -3
- package/src/lib/utils/excalidraw/__snapshots__/putExcalidrawContent.test.tsx.snap +5 -5
- package/src/lib/utils/tldr/__snapshots__/buildFromV1Document.test.ts.snap +4 -4
- package/src/test/A11y.test.tsx +3 -2
- package/src/test/ClickManager.test.ts +7 -6
- package/src/test/Editor.test.tsx +20 -19
- package/src/test/EraserTool.test.ts +184 -13
- package/src/test/HandTool.test.ts +10 -9
- package/src/test/HighlightShape.test.ts +2 -1
- package/src/test/SelectTool.test.ts +3 -2
- package/src/test/TLUserPreferences.test.ts +4 -3
- package/src/test/TestEditor.ts +13 -15
- package/src/test/TldrawEditor.test.tsx +11 -10
- package/src/test/ZoomTool.test.ts +7 -6
- package/src/test/__snapshots__/drawing.test.ts.snap +2 -2
- package/src/test/__snapshots__/groups.test.tsx.snap +6 -6
- package/src/test/__snapshots__/resizing.test.ts.snap +2 -2
- package/src/test/arrows-megabus.test.tsx +5 -4
- package/src/test/bindings.test.tsx +24 -37
- package/src/test/bookmark-shapes.test.ts +1 -8
- package/src/test/commands/__snapshots__/getSvgString.test.ts.snap +23 -7
- package/src/test/commands/__snapshots__/packShapes.test.ts.snap +8 -8
- package/src/test/commands/__snapshots__/zoomToFit.test.ts.snap +2 -2
- package/src/test/commands/alignShapes.test.tsx +25 -24
- package/src/test/commands/animationSpeed.test.ts +2 -1
- package/src/test/commands/centerOnPoint.test.ts +3 -2
- package/src/test/commands/clipboard.test.ts +3 -2
- package/src/test/commands/createShapes.test.ts +2 -1
- package/src/test/commands/deleteShapes.test.ts +2 -1
- package/src/test/commands/distributeShapes.test.tsx +11 -10
- package/src/test/commands/getSvgString.test.ts +2 -1
- package/src/test/commands/packShapes.test.ts +5 -4
- package/src/test/commands/resizeShape.test.ts +2 -1
- package/src/test/commands/rotateShapes.test.ts +7 -6
- package/src/test/commands/setCamera.test.ts +4 -3
- package/src/test/commands/setCurrentPage.test.ts +3 -2
- package/src/test/commands/stackShapes.test.ts +11 -10
- package/src/test/commands/stretch.test.tsx +13 -12
- package/src/test/createDeepLink.test.tsx +2 -1
- package/src/test/cropping.test.ts +3 -2
- package/src/test/drawing.test.ts +2 -1
- package/src/test/flipShapes.test.ts +4 -3
- package/src/test/frames.test.ts +25 -24
- package/src/test/getCulledShapes.test.tsx +3 -2
- package/src/test/groups.test.tsx +1 -1
- package/src/test/handleDeepLink.test.tsx +2 -1
- package/src/test/maxShapes.test.ts +3 -2
- package/src/test/modifiers.test.ts +5 -4
- package/src/test/navigation.test.ts +12 -11
- package/src/test/panning.test.ts +2 -1
- package/src/test/perf/perf.test.ts +2 -1
- package/src/test/registerDeepLinkListener.test.tsx +10 -9
- package/src/test/resizing.test.ts +39 -38
- package/src/test/select.test.tsx +4 -3
- package/src/test/selection-omnibus.test.ts +11 -10
- package/src/test/shapeutils.test.ts +4 -3
- package/src/test/translating.test.ts +9 -8
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { createShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from '../TestEditor'
|
|
3
4
|
|
|
4
5
|
let editor: TestEditor
|
|
@@ -10,7 +11,7 @@ const ids = {
|
|
|
10
11
|
boxD: createShapeId('boxD'),
|
|
11
12
|
}
|
|
12
13
|
|
|
13
|
-
|
|
14
|
+
vi.useFakeTimers()
|
|
14
15
|
|
|
15
16
|
beforeEach(() => {
|
|
16
17
|
editor = new TestEditor()
|
|
@@ -45,7 +46,7 @@ describe('editor.packShapes', () => {
|
|
|
45
46
|
editor.selectAll()
|
|
46
47
|
const centerBefore = editor.getSelectionRotatedPageBounds()!.center.clone()
|
|
47
48
|
editor.packShapes(editor.getSelectedShapeIds())
|
|
48
|
-
|
|
49
|
+
vi.advanceTimersByTime(1000)
|
|
49
50
|
expect(
|
|
50
51
|
editor.getCurrentPageShapes().map((s) => ({ ...s, parentId: 'wahtever' }))
|
|
51
52
|
).toMatchSnapshot('packed shapes')
|
|
@@ -57,7 +58,7 @@ describe('editor.packShapes', () => {
|
|
|
57
58
|
editor.selectAll()
|
|
58
59
|
const centerBefore = editor.getSelectionRotatedPageBounds()!.center.clone()
|
|
59
60
|
editor.packShapes(editor.getSelectedShapeIds(), 16)
|
|
60
|
-
|
|
61
|
+
vi.advanceTimersByTime(1000)
|
|
61
62
|
expect(
|
|
62
63
|
editor.getCurrentPageShapes().map((s) => ({ ...s, parentId: 'wahtever' }))
|
|
63
64
|
).toMatchSnapshot('packed shapes')
|
|
@@ -68,7 +69,7 @@ describe('editor.packShapes', () => {
|
|
|
68
69
|
it('packs rotated shapes', () => {
|
|
69
70
|
editor.updateShapes([{ id: ids.boxA, type: 'geo', rotation: Math.PI }])
|
|
70
71
|
editor.selectAll().packShapes(editor.getSelectedShapeIds(), 16)
|
|
71
|
-
|
|
72
|
+
vi.advanceTimersByTime(1000)
|
|
72
73
|
expect(
|
|
73
74
|
editor.getCurrentPageShapes().map((s) => ({ ...s, parentId: 'wahtever' }))
|
|
74
75
|
).toMatchSnapshot('packed shapes')
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { createShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from '../TestEditor'
|
|
3
4
|
|
|
4
5
|
let editor: TestEditor
|
|
@@ -40,20 +41,20 @@ beforeEach(() => {
|
|
|
40
41
|
})
|
|
41
42
|
|
|
42
43
|
describe('editor.rotateShapesBy', () => {
|
|
43
|
-
let fnStart =
|
|
44
|
-
let fnChange =
|
|
45
|
-
let fnEnd =
|
|
44
|
+
let fnStart = vi.fn()
|
|
45
|
+
let fnChange = vi.fn()
|
|
46
|
+
let fnEnd = vi.fn()
|
|
46
47
|
|
|
47
48
|
beforeEach(() => {
|
|
48
49
|
// Set start / change / end events on only the geo shape
|
|
49
50
|
const util = editor.getShapeUtil('geo')
|
|
50
51
|
|
|
51
52
|
// Bad! who did this (did I do this)
|
|
52
|
-
util.onRotateStart = fnStart =
|
|
53
|
+
util.onRotateStart = fnStart = vi.fn()
|
|
53
54
|
|
|
54
|
-
util.onRotate = fnChange =
|
|
55
|
+
util.onRotate = fnChange = vi.fn()
|
|
55
56
|
|
|
56
|
-
util.onRotateEnd = fnEnd =
|
|
57
|
+
util.onRotateEnd = fnEnd = vi.fn()
|
|
57
58
|
})
|
|
58
59
|
it('Rotates shapes and fires events', () => {
|
|
59
60
|
// Select the shape...
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { Box, DEFAULT_CAMERA_OPTIONS, Vec, createShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from '../TestEditor'
|
|
3
4
|
|
|
4
5
|
let editor: TestEditor
|
|
@@ -366,14 +367,14 @@ describe('CameraOptions.zoomSpeed', () => {
|
|
|
366
367
|
editor.setCameraOptions({ ...DEFAULT_CAMERA_OPTIONS, zoomSpeed: 2 })
|
|
367
368
|
expect(editor.getCamera()).toMatchObject({ x: 0, y: 0, z: 1 })
|
|
368
369
|
editor.setCurrentTool('zoom').click()
|
|
369
|
-
|
|
370
|
+
vi.advanceTimersByTime(300)
|
|
370
371
|
expect(editor.getCamera()).toMatchObject({ x: 0, y: 0, z: 2 })
|
|
371
372
|
})
|
|
372
373
|
it('Does not affect zoom tool zooming (0.5x)', () => {
|
|
373
374
|
editor.setCameraOptions({ ...DEFAULT_CAMERA_OPTIONS, zoomSpeed: 0.5 })
|
|
374
375
|
expect(editor.getCamera()).toMatchObject({ x: 0, y: 0, z: 1 })
|
|
375
376
|
editor.setCurrentTool('zoom').click()
|
|
376
|
-
|
|
377
|
+
vi.advanceTimersByTime(300)
|
|
377
378
|
expect(editor.getCamera()).toMatchObject({ x: 0, y: 0, z: 2 })
|
|
378
379
|
})
|
|
379
380
|
it('Does not affect editor zoom method (2x)', () => {
|
|
@@ -1028,7 +1029,7 @@ describe('Allows mixed values for x and y', () => {
|
|
|
1028
1029
|
|
|
1029
1030
|
test('it animated towards the constrained viewport rather than the given viewport', () => {
|
|
1030
1031
|
// @ts-expect-error
|
|
1031
|
-
const mockAnimateToViewport = (editor._animateToViewport =
|
|
1032
|
+
const mockAnimateToViewport = (editor._animateToViewport = vi.fn())
|
|
1032
1033
|
editor.setCameraOptions({
|
|
1033
1034
|
...DEFAULT_CAMERA_OPTIONS,
|
|
1034
1035
|
constraints: {
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { IndexKey, PageRecordType, TLPageId, createShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from '../TestEditor'
|
|
3
4
|
|
|
4
5
|
let editor: TestEditor
|
|
@@ -76,7 +77,7 @@ describe('setCurrentPage', () => {
|
|
|
76
77
|
it('logs an error when trying to navigate to a page that does not exist', () => {
|
|
77
78
|
const initialPageId = editor.getCurrentPageId()
|
|
78
79
|
expect(editor.getCurrentPageId()).toBe(initialPageId)
|
|
79
|
-
console.error =
|
|
80
|
+
console.error = vi.fn()
|
|
80
81
|
|
|
81
82
|
expect(() => {
|
|
82
83
|
editor.setCurrentPage('page:does-not-exist' as TLPageId)
|
|
@@ -105,7 +106,7 @@ describe('setCurrentPage', () => {
|
|
|
105
106
|
})
|
|
106
107
|
|
|
107
108
|
it('applies camera constraints', () => {
|
|
108
|
-
const spy =
|
|
109
|
+
const spy = vi.spyOn(editor, 'setCamera')
|
|
109
110
|
|
|
110
111
|
let currentPageId = editor.getCurrentPageId()
|
|
111
112
|
expect(currentPageId).toMatchInlineSnapshot(`"page:page"`)
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { createShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from '../TestEditor'
|
|
3
4
|
|
|
4
|
-
|
|
5
|
+
vi.useFakeTimers()
|
|
5
6
|
|
|
6
7
|
let editor: TestEditor
|
|
7
8
|
|
|
@@ -51,10 +52,10 @@ describe('distributeShapes command', () => {
|
|
|
51
52
|
describe('when less than three shapes are selected', () => {
|
|
52
53
|
it('does nothing', () => {
|
|
53
54
|
editor.setSelectedShapes([ids.boxA, ids.boxB])
|
|
54
|
-
const fn =
|
|
55
|
+
const fn = vi.fn()
|
|
55
56
|
editor.store.listen(fn)
|
|
56
57
|
editor.stackShapes(editor.getSelectedShapeIds(), 'horizontal', 0)
|
|
57
|
-
|
|
58
|
+
vi.advanceTimersByTime(1000)
|
|
58
59
|
expect(fn).not.toHaveBeenCalled()
|
|
59
60
|
})
|
|
60
61
|
})
|
|
@@ -65,7 +66,7 @@ describe('distributeShapes command', () => {
|
|
|
65
66
|
// @ts-expect-error
|
|
66
67
|
editor.options.adjacentShapeMargin = 1
|
|
67
68
|
editor.stackShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
68
|
-
|
|
69
|
+
vi.advanceTimersByTime(1000)
|
|
69
70
|
// 200 distance gap between c and d
|
|
70
71
|
editor.expectShapeToMatch({
|
|
71
72
|
id: ids.boxA,
|
|
@@ -92,7 +93,7 @@ describe('distributeShapes command', () => {
|
|
|
92
93
|
it('stacks the shapes based on a given value', () => {
|
|
93
94
|
editor.setSelectedShapes([ids.boxA, ids.boxB, ids.boxC, ids.boxD])
|
|
94
95
|
editor.stackShapes(editor.getSelectedShapeIds(), 'horizontal', 10)
|
|
95
|
-
|
|
96
|
+
vi.advanceTimersByTime(1000)
|
|
96
97
|
// 200 distance gap between c and d
|
|
97
98
|
editor.expectShapeToMatch({
|
|
98
99
|
id: ids.boxA,
|
|
@@ -119,7 +120,7 @@ describe('distributeShapes command', () => {
|
|
|
119
120
|
it('stacks the shapes based on the most common gap', () => {
|
|
120
121
|
editor.setSelectedShapes([ids.boxA, ids.boxB, ids.boxC, ids.boxD])
|
|
121
122
|
editor.stackShapes(editor.getSelectedShapeIds(), 'horizontal', 0)
|
|
122
|
-
|
|
123
|
+
vi.advanceTimersByTime(1000)
|
|
123
124
|
// 200 distance gap between c and d
|
|
124
125
|
editor.expectShapeToMatch({
|
|
125
126
|
id: ids.boxA,
|
|
@@ -147,7 +148,7 @@ describe('distributeShapes command', () => {
|
|
|
147
148
|
editor.updateShapes([{ id: ids.boxD, type: 'geo', x: 540, y: 700 }])
|
|
148
149
|
editor.setSelectedShapes([ids.boxA, ids.boxB, ids.boxC, ids.boxD])
|
|
149
150
|
editor.stackShapes(editor.getSelectedShapeIds(), 'horizontal', 0)
|
|
150
|
-
|
|
151
|
+
vi.advanceTimersByTime(1000)
|
|
151
152
|
editor.expectShapeToMatch({
|
|
152
153
|
id: ids.boxA,
|
|
153
154
|
x: 0,
|
|
@@ -175,7 +176,7 @@ describe('distributeShapes command', () => {
|
|
|
175
176
|
it('stacks the shapes based on a given value', () => {
|
|
176
177
|
editor.setSelectedShapes([ids.boxA, ids.boxB, ids.boxC, ids.boxD])
|
|
177
178
|
editor.stackShapes(editor.getSelectedShapeIds(), 'vertical', 10)
|
|
178
|
-
|
|
179
|
+
vi.advanceTimersByTime(1000)
|
|
179
180
|
// 200 distance gap between c and d
|
|
180
181
|
editor.expectShapeToMatch({
|
|
181
182
|
id: ids.boxA,
|
|
@@ -202,7 +203,7 @@ describe('distributeShapes command', () => {
|
|
|
202
203
|
it('stacks the shapes based on the most common gap', () => {
|
|
203
204
|
editor.setSelectedShapes([ids.boxA, ids.boxB, ids.boxC, ids.boxD])
|
|
204
205
|
editor.stackShapes(editor.getSelectedShapeIds(), 'vertical', 0)
|
|
205
|
-
|
|
206
|
+
vi.advanceTimersByTime(1000)
|
|
206
207
|
// 200 distance gap between c and d
|
|
207
208
|
editor.expectShapeToMatch({
|
|
208
209
|
id: ids.boxA,
|
|
@@ -230,7 +231,7 @@ describe('distributeShapes command', () => {
|
|
|
230
231
|
editor.updateShapes([{ id: ids.boxD, type: 'geo', x: 700, y: 540 }])
|
|
231
232
|
editor.setSelectedShapes([ids.boxA, ids.boxB, ids.boxC, ids.boxD])
|
|
232
233
|
editor.stackShapes(editor.getSelectedShapeIds(), 'vertical', 0)
|
|
233
|
-
|
|
234
|
+
vi.advanceTimersByTime(1000)
|
|
234
235
|
editor.expectShapeToMatch({
|
|
235
236
|
id: ids.boxA,
|
|
236
237
|
x: 0,
|
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
import { PI, TLShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from '../TestEditor'
|
|
3
4
|
import { TL } from '../test-jsx'
|
|
4
5
|
|
|
5
6
|
let editor: TestEditor
|
|
6
7
|
let ids: Record<string, TLShapeId>
|
|
7
8
|
|
|
8
|
-
|
|
9
|
+
vi.useFakeTimers()
|
|
9
10
|
|
|
10
11
|
function createVideoShape() {
|
|
11
12
|
return editor.createShapesFromJsx(<TL.video ref="video1" x={0} y={0} w={160} h={90} />).video1
|
|
@@ -26,10 +27,10 @@ beforeEach(() => {
|
|
|
26
27
|
describe('when less than two shapes are selected', () => {
|
|
27
28
|
it('does nothing', () => {
|
|
28
29
|
editor.setSelectedShapes([ids.boxB])
|
|
29
|
-
const fn =
|
|
30
|
+
const fn = vi.fn()
|
|
30
31
|
editor.store.listen(fn)
|
|
31
32
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
32
|
-
|
|
33
|
+
vi.advanceTimersByTime(1000)
|
|
33
34
|
|
|
34
35
|
expect(fn).not.toHaveBeenCalled()
|
|
35
36
|
})
|
|
@@ -39,7 +40,7 @@ describe('when multiple shapes are selected', () => {
|
|
|
39
40
|
it('stretches horizontally', () => {
|
|
40
41
|
editor.selectAll()
|
|
41
42
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
42
|
-
|
|
43
|
+
vi.advanceTimersByTime(1000)
|
|
43
44
|
editor.expectShapeToMatch(
|
|
44
45
|
{ id: ids.boxA, x: 0, y: 0, props: { w: 500 } },
|
|
45
46
|
{ id: ids.boxB, x: 0, y: 100, props: { w: 500 } },
|
|
@@ -52,7 +53,7 @@ describe('when multiple shapes are selected', () => {
|
|
|
52
53
|
editor.selectAll()
|
|
53
54
|
expect(editor.getSelectedShapes().length).toBe(4)
|
|
54
55
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
55
|
-
|
|
56
|
+
vi.advanceTimersByTime(1000)
|
|
56
57
|
const newHeight = (500 * 9) / 16
|
|
57
58
|
editor.expectShapeToMatch(
|
|
58
59
|
{ id: ids.boxA, x: 0, y: 0, props: { w: 500 } },
|
|
@@ -65,7 +66,7 @@ describe('when multiple shapes are selected', () => {
|
|
|
65
66
|
it('stretches vertically', () => {
|
|
66
67
|
editor.selectAll()
|
|
67
68
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'vertical')
|
|
68
|
-
|
|
69
|
+
vi.advanceTimersByTime(1000)
|
|
69
70
|
editor.expectShapeToMatch(
|
|
70
71
|
{ id: ids.boxA, x: 0, y: 0, props: { h: 500 } },
|
|
71
72
|
{ id: ids.boxB, x: 100, y: 0, props: { h: 500 } },
|
|
@@ -78,7 +79,7 @@ describe('when multiple shapes are selected', () => {
|
|
|
78
79
|
editor.selectAll()
|
|
79
80
|
expect(editor.getSelectedShapes().length).toBe(4)
|
|
80
81
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'vertical')
|
|
81
|
-
|
|
82
|
+
vi.advanceTimersByTime(1000)
|
|
82
83
|
const newWidth = (500 * 16) / 9
|
|
83
84
|
editor.expectShapeToMatch(
|
|
84
85
|
{ id: ids.boxA, x: 0, y: 0, props: { h: 500 } },
|
|
@@ -91,7 +92,7 @@ describe('when multiple shapes are selected', () => {
|
|
|
91
92
|
it('does, undoes and redoes command', () => {
|
|
92
93
|
editor.markHistoryStoppingPoint('stretch')
|
|
93
94
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
94
|
-
|
|
95
|
+
vi.advanceTimersByTime(1000)
|
|
95
96
|
|
|
96
97
|
editor.expectShapeToMatch({ id: ids.boxB, x: 0, props: { w: 500 } })
|
|
97
98
|
editor.undo()
|
|
@@ -106,7 +107,7 @@ describe('When shapes are the child of another shape.', () => {
|
|
|
106
107
|
editor.reparentShapes([ids.boxB], ids.boxA)
|
|
107
108
|
editor.select(ids.boxB, ids.boxC)
|
|
108
109
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
109
|
-
|
|
110
|
+
vi.advanceTimersByTime(1000)
|
|
110
111
|
editor.expectShapeToMatch(
|
|
111
112
|
{ id: ids.boxB, x: 100, y: 100, props: { w: 400 } },
|
|
112
113
|
{ id: ids.boxC, x: 100, y: 400, props: { w: 400 } }
|
|
@@ -117,7 +118,7 @@ describe('When shapes are the child of another shape.', () => {
|
|
|
117
118
|
editor.reparentShapes([ids.boxB], ids.boxA)
|
|
118
119
|
editor.select(ids.boxB, ids.boxC)
|
|
119
120
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'vertical')
|
|
120
|
-
|
|
121
|
+
vi.advanceTimersByTime(1000)
|
|
121
122
|
editor.expectShapeToMatch(
|
|
122
123
|
{ id: ids.boxB, x: 100, y: 100, props: { h: 400 } },
|
|
123
124
|
{ id: ids.boxC, x: 400, y: 100, props: { h: 400 } }
|
|
@@ -140,7 +141,7 @@ describe('When shapes are the child of a rotated shape.', () => {
|
|
|
140
141
|
|
|
141
142
|
editor.select(ids.boxA, ids.boxC)
|
|
142
143
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
143
|
-
|
|
144
|
+
vi.advanceTimersByTime(1000)
|
|
144
145
|
editor.expectShapeToMatch(
|
|
145
146
|
{
|
|
146
147
|
id: ids.boxA,
|
|
@@ -184,7 +185,7 @@ describe('When shapes are the child of a rotated shape.', () => {
|
|
|
184
185
|
editor.selectAll()
|
|
185
186
|
|
|
186
187
|
editor.stretchShapes(editor.getSelectedShapeIds(), 'vertical')
|
|
187
|
-
|
|
188
|
+
vi.advanceTimersByTime(1000)
|
|
188
189
|
editor.expectShapeToMatch(
|
|
189
190
|
{
|
|
190
191
|
id: ids.boxA,
|
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
import { createShapeId, TLImageShape } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { MIN_CROP_SIZE } from '../lib/shapes/shared/crop'
|
|
3
4
|
import { TestEditor } from './TestEditor'
|
|
4
5
|
|
|
5
|
-
|
|
6
|
+
vi.useFakeTimers()
|
|
6
7
|
|
|
7
8
|
let editor: TestEditor
|
|
8
9
|
|
|
@@ -495,7 +496,7 @@ describe('When in the select.crop.translating_crop state', () => {
|
|
|
495
496
|
})
|
|
496
497
|
|
|
497
498
|
editor.keyUp('Shift')
|
|
498
|
-
|
|
499
|
+
vi.advanceTimersByTime(500)
|
|
499
500
|
|
|
500
501
|
const afterShiftUp = editor.getShape<TLImageShape>(ids.imageB)!.props.crop!
|
|
501
502
|
|
package/src/test/drawing.test.ts
CHANGED
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
import { TLDrawShape, TLHighlightShape, last } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from './TestEditor'
|
|
3
4
|
import { TEST_DRAW_SHAPE_SCREEN_POINTS } from './drawing.data'
|
|
4
5
|
|
|
5
|
-
|
|
6
|
+
vi.useFakeTimers()
|
|
6
7
|
|
|
7
8
|
let editor: TestEditor
|
|
8
9
|
|
|
@@ -10,12 +10,13 @@ import {
|
|
|
10
10
|
createBindingId,
|
|
11
11
|
createShapeId,
|
|
12
12
|
} from '@tldraw/editor'
|
|
13
|
+
import { vi } from 'vitest'
|
|
13
14
|
import { getArrowBindings } from '../lib/shapes/arrow/shared'
|
|
14
15
|
import { TestEditor } from './TestEditor'
|
|
15
16
|
|
|
16
17
|
let editor: TestEditor
|
|
17
18
|
|
|
18
|
-
|
|
19
|
+
vi.useFakeTimers()
|
|
19
20
|
|
|
20
21
|
const ids = {
|
|
21
22
|
boxA: createShapeId('boxA'),
|
|
@@ -297,7 +298,7 @@ describe('When one shape is selected', () => {
|
|
|
297
298
|
})
|
|
298
299
|
|
|
299
300
|
it('Flips the direct child shape positions if the shape is a group', async () => {
|
|
300
|
-
const fn =
|
|
301
|
+
const fn = vi.fn()
|
|
301
302
|
|
|
302
303
|
editor.selectAll()
|
|
303
304
|
editor.groupShapes(editor.getSelectedShapeIds()) // this will also select the new group
|
|
@@ -306,7 +307,7 @@ describe('When one shape is selected', () => {
|
|
|
306
307
|
editor.flipShapes(editor.getSelectedShapeIds(), 'horizontal')
|
|
307
308
|
|
|
308
309
|
// The change event should have been called
|
|
309
|
-
|
|
310
|
+
vi.runOnlyPendingTimers()
|
|
310
311
|
expect(fn).toHaveBeenCalled()
|
|
311
312
|
|
|
312
313
|
editor.expectShapeToMatch(
|
package/src/test/frames.test.ts
CHANGED
|
@@ -8,13 +8,14 @@ import {
|
|
|
8
8
|
createShapeId,
|
|
9
9
|
toRichText,
|
|
10
10
|
} from '@tldraw/editor'
|
|
11
|
+
import { vi } from 'vitest'
|
|
11
12
|
import { getArrowBindings } from '../lib/shapes/arrow/shared'
|
|
12
13
|
import { DEFAULT_FRAME_PADDING, fitFrameToContent, removeFrame } from '../lib/utils/frames/frames'
|
|
13
14
|
import { TestEditor } from './TestEditor'
|
|
14
15
|
|
|
15
16
|
let editor: TestEditor
|
|
16
17
|
|
|
17
|
-
|
|
18
|
+
vi.useFakeTimers()
|
|
18
19
|
|
|
19
20
|
beforeEach(() => {
|
|
20
21
|
editor = new TestEditor()
|
|
@@ -335,7 +336,7 @@ describe('frame shapes', () => {
|
|
|
335
336
|
// move to the center of the frame
|
|
336
337
|
editor.pointerMove(100, 100)
|
|
337
338
|
|
|
338
|
-
|
|
339
|
+
vi.advanceTimersByTime(300)
|
|
339
340
|
|
|
340
341
|
// Expect the shape to be inside the frame
|
|
341
342
|
expect(editor.getOnlySelectedShape()!.id).toBe(ids.boxA)
|
|
@@ -343,13 +344,13 @@ describe('frame shapes', () => {
|
|
|
343
344
|
|
|
344
345
|
// Move out of the frame
|
|
345
346
|
editor.pointerMove(275, 275)
|
|
346
|
-
|
|
347
|
+
vi.advanceTimersByTime(250)
|
|
347
348
|
|
|
348
349
|
expect(editor.getOnlySelectedShape()!.parentId).toBe(editor.getCurrentPageId())
|
|
349
350
|
|
|
350
351
|
// Move back into the frame
|
|
351
352
|
editor.pointerMove(150, 150)
|
|
352
|
-
|
|
353
|
+
vi.advanceTimersByTime(250)
|
|
353
354
|
|
|
354
355
|
// Expect the shape to be inside the frame again
|
|
355
356
|
expect(editor.getOnlySelectedShape()!.parentId).toBe(frameId)
|
|
@@ -384,7 +385,7 @@ describe('frame shapes', () => {
|
|
|
384
385
|
|
|
385
386
|
editor.setCurrentTool('select').select(box1.id).pointerDown(127, 127).pointerMove(132, 127)
|
|
386
387
|
|
|
387
|
-
|
|
388
|
+
vi.advanceTimersByTime(250)
|
|
388
389
|
|
|
389
390
|
expect(editor.getOnlySelectedShape()!.id).toBe(box1.id)
|
|
390
391
|
if (editor.getShape(box1)?.parentId !== frame.id) {
|
|
@@ -403,14 +404,14 @@ describe('frame shapes', () => {
|
|
|
403
404
|
editor.pointerMove(175, 175)
|
|
404
405
|
expect(editor.getOnlySelectedShape()!.parentId).toBe(frame.id)
|
|
405
406
|
|
|
406
|
-
|
|
407
|
+
vi.advanceTimersByTime(250)
|
|
407
408
|
expect(editor.getOnlySelectedShape()!.parentId).toBe(frame.id)
|
|
408
409
|
|
|
409
410
|
// Let's try that
|
|
410
411
|
editor.pointerMove(1750, 1750)
|
|
411
|
-
|
|
412
|
+
vi.advanceTimersByTime(200)
|
|
412
413
|
editor.pointerMove(175, 175)
|
|
413
|
-
|
|
414
|
+
vi.advanceTimersByTime(200)
|
|
414
415
|
|
|
415
416
|
// yay
|
|
416
417
|
expect(editor.getHintingShapeIds()).toHaveLength(1)
|
|
@@ -958,7 +959,7 @@ describe('When dragging a shape inside a group inside a frame', () => {
|
|
|
958
959
|
editor.pointerMove(150, 150).pointerDown(150, 150).pointerMove(140, 140)
|
|
959
960
|
|
|
960
961
|
expect(editor.getOnlySelectedShapeId()).toBe(ids.box1)
|
|
961
|
-
|
|
962
|
+
vi.advanceTimersByTime(300)
|
|
962
963
|
|
|
963
964
|
expect(editor.getShape(ids.box1)!.parentId).toBe(ids.group1)
|
|
964
965
|
})
|
|
@@ -973,7 +974,7 @@ it('Drags into a frame', () => {
|
|
|
973
974
|
editor.pointerDown(550, 550)
|
|
974
975
|
editor.pointerMove(250, 250)
|
|
975
976
|
|
|
976
|
-
|
|
977
|
+
vi.advanceTimersByTime(200)
|
|
977
978
|
|
|
978
979
|
expect(editor.getShape(box1)!.parentId).toBe(frame.id)
|
|
979
980
|
})
|
|
@@ -992,7 +993,7 @@ it('Allows dragging grouped shapes into frames if every shape in the group is in
|
|
|
992
993
|
editor.pointerDown(1100, 1100)
|
|
993
994
|
editor.pointerMove(250, 250)
|
|
994
995
|
|
|
995
|
-
|
|
996
|
+
vi.advanceTimersByTime(250)
|
|
996
997
|
|
|
997
998
|
expect(editor.getHintingShapeIds()).toMatchObject([frame.id])
|
|
998
999
|
|
|
@@ -1068,7 +1069,7 @@ describe('When dragging a shape', () => {
|
|
|
1068
1069
|
editor.pointerMove(30, 50)
|
|
1069
1070
|
editor.pointerUp(30, 50)
|
|
1070
1071
|
const parent = editor.getShape(rectId)?.parentId
|
|
1071
|
-
|
|
1072
|
+
vi.advanceTimersByTime(200)
|
|
1072
1073
|
expect(parent).toBe(frameId)
|
|
1073
1074
|
})
|
|
1074
1075
|
|
|
@@ -1185,7 +1186,7 @@ describe('Unparenting behavior', () => {
|
|
|
1185
1186
|
// expect(editor.getShape(rect.id)!.parentId).toBe(frame.id)
|
|
1186
1187
|
// editor.pointerDown(90, 50)
|
|
1187
1188
|
// editor.pointerMove(110, 50)
|
|
1188
|
-
//
|
|
1189
|
+
// vi.advanceTimersByTime(200)
|
|
1189
1190
|
// expect(editor.getShape(rect.id)!.parentId).toBe(editor.getCurrentPageId())
|
|
1190
1191
|
// editor.pointerUp(110, 50)
|
|
1191
1192
|
// expect(editor.getShape(rect.id)!.parentId).toBe(editor.getCurrentPageId())
|
|
@@ -1199,7 +1200,7 @@ describe('Unparenting behavior', () => {
|
|
|
1199
1200
|
expect(editor.getShape(rect.id)!.parentId).toBe(frame.id)
|
|
1200
1201
|
editor.pointerDown(90, 50)
|
|
1201
1202
|
editor.pointerMove(110, 50)
|
|
1202
|
-
|
|
1203
|
+
vi.advanceTimersByTime(200)
|
|
1203
1204
|
expect(editor.getShape(rect.id)!.parentId).toBe(editor.getCurrentPageId())
|
|
1204
1205
|
editor.pointerUp(110, 50)
|
|
1205
1206
|
expect(editor.getShape(rect.id)!.parentId).toBe(editor.getCurrentPageId())
|
|
@@ -1299,7 +1300,7 @@ describe('Unparenting behavior', () => {
|
|
|
1299
1300
|
expect(editor.getShape(triangle.id)!.parentId).toBe(frame.id)
|
|
1300
1301
|
|
|
1301
1302
|
// But after a delay, the triangle is reparented because it's not overlapping
|
|
1302
|
-
|
|
1303
|
+
vi.advanceTimersByTime(200)
|
|
1303
1304
|
expect(editor.getShape(triangle.id)!.parentId).toBe(editor.getCurrentPageId())
|
|
1304
1305
|
|
|
1305
1306
|
editor.pointerMove(50, 50)
|
|
@@ -1308,7 +1309,7 @@ describe('Unparenting behavior', () => {
|
|
|
1308
1309
|
expect(editor.getShape(triangle.id)!.parentId).toBe(editor.getCurrentPageId())
|
|
1309
1310
|
|
|
1310
1311
|
// But after a delay, the triangle is reparented because it's overlapping
|
|
1311
|
-
|
|
1312
|
+
vi.advanceTimersByTime(200)
|
|
1312
1313
|
expect(editor.getShape(triangle.id)!.parentId).toBe(frame.id)
|
|
1313
1314
|
})
|
|
1314
1315
|
|
|
@@ -1348,12 +1349,12 @@ describe('Unparenting behavior', () => {
|
|
|
1348
1349
|
expect(editor.isIn('select.translating')).toBe(true)
|
|
1349
1350
|
|
|
1350
1351
|
// Wait for reparenting to happen
|
|
1351
|
-
|
|
1352
|
+
vi.advanceTimersByTime(250)
|
|
1352
1353
|
expect(editor.getShape(largeRect.id)!.parentId).toBe(frameId)
|
|
1353
1354
|
|
|
1354
1355
|
// The large rectangle should now be reparented to the frame, even though the frame covers it
|
|
1355
1356
|
editor.pointerUp(250, 250)
|
|
1356
|
-
|
|
1357
|
+
vi.advanceTimersByTime(250)
|
|
1357
1358
|
}
|
|
1358
1359
|
|
|
1359
1360
|
// When the shape has no fill and an empty label, it should fall out of the frame
|
|
@@ -1503,7 +1504,7 @@ describe('When dragging groups or shapes within a group', () => {
|
|
|
1503
1504
|
editor.pointerDown(1100, 1100)
|
|
1504
1505
|
editor.pointerMove(250, 250)
|
|
1505
1506
|
|
|
1506
|
-
|
|
1507
|
+
vi.advanceTimersByTime(200)
|
|
1507
1508
|
|
|
1508
1509
|
expect(editor.getShape(group)!.parentId).toBe(frame.id)
|
|
1509
1510
|
})
|
|
@@ -1526,14 +1527,14 @@ describe('When dragging groups or shapes within a group', () => {
|
|
|
1526
1527
|
editor.select(rect1ID)
|
|
1527
1528
|
editor.pointerDown(15, 15)
|
|
1528
1529
|
editor.pointerMove(100, 100)
|
|
1529
|
-
|
|
1530
|
+
vi.advanceTimersByTime(200)
|
|
1530
1531
|
|
|
1531
1532
|
expect(editor.getShape(rect1ID)?.parentId).toBe(group.id)
|
|
1532
1533
|
expect(editor.getShape(rect2ID)?.parentId).toBe(group.id)
|
|
1533
1534
|
expect(group.parentId).toBe(frame.id)
|
|
1534
1535
|
|
|
1535
1536
|
editor.pointerUp(100, 100)
|
|
1536
|
-
|
|
1537
|
+
vi.advanceTimersByTime(200)
|
|
1537
1538
|
|
|
1538
1539
|
expect(editor.getShape(rect1ID)?.parentId).toBe(group.id)
|
|
1539
1540
|
expect(editor.getShape(rect2ID)?.parentId).toBe(group.id)
|
|
@@ -1558,7 +1559,7 @@ describe('When dragging groups or shapes within a group', () => {
|
|
|
1558
1559
|
editor.pointerDown(15, 15)
|
|
1559
1560
|
editor.pointerMove(200, 200)
|
|
1560
1561
|
|
|
1561
|
-
|
|
1562
|
+
vi.advanceTimersByTime(200)
|
|
1562
1563
|
expect(editor.getShape(rect1ID)?.parentId).toBe(group.id)
|
|
1563
1564
|
expect(editor.getShape(rect2ID)?.parentId).toBe(group.id)
|
|
1564
1565
|
expect(editor.getShape(group.id)?.parentId).toBe(editor.getCurrentPageId())
|
|
@@ -1587,7 +1588,7 @@ describe('When dragging groups or shapes within a group', () => {
|
|
|
1587
1588
|
editor.pointerDown(15, 15)
|
|
1588
1589
|
editor.pointerMove(200, 200)
|
|
1589
1590
|
|
|
1590
|
-
|
|
1591
|
+
vi.advanceTimersByTime(200)
|
|
1591
1592
|
expect(editor.getShape(rect1ID)?.parentId).toBe(group.id)
|
|
1592
1593
|
expect(editor.getShape(rect2ID)?.parentId).toBe(group.id)
|
|
1593
1594
|
expect(editor.getShape(group.id)?.parentId).toBe(editor.getCurrentPageId())
|
|
@@ -1638,7 +1639,7 @@ describe('When dragging groups or shapes within a group', () => {
|
|
|
1638
1639
|
editor.pointerDown(215, 215)
|
|
1639
1640
|
editor.pointerMove(15, 15)
|
|
1640
1641
|
|
|
1641
|
-
|
|
1642
|
+
vi.advanceTimersByTime(200)
|
|
1642
1643
|
expect(editor.getShape(rect1ID)?.parentId).toBe(group.id)
|
|
1643
1644
|
expect(editor.getShape(rect2ID)?.parentId).toBe(group.id)
|
|
1644
1645
|
expect(editor.getShape(group.id)?.parentId).toBe(frameID)
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { Box, TLShapeId, createShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from './TestEditor'
|
|
3
4
|
import { TL } from './test-jsx'
|
|
4
5
|
|
|
@@ -28,13 +29,13 @@ it('lists shapes in viewport', () => {
|
|
|
28
29
|
|
|
29
30
|
// Move the camera 201 pixels to the right and 201 pixels down
|
|
30
31
|
editor.pan({ x: -201, y: -201 })
|
|
31
|
-
|
|
32
|
+
vi.advanceTimersByTime(500)
|
|
32
33
|
|
|
33
34
|
// A is now outside of the viewport, like D
|
|
34
35
|
expect(editor.getCulledShapes()).toStrictEqual(new Set([ids.A, ids.D]))
|
|
35
36
|
|
|
36
37
|
editor.pan({ x: -900, y: -900 })
|
|
37
|
-
|
|
38
|
+
vi.advanceTimersByTime(500)
|
|
38
39
|
// Now all shapes are outside of the viewport, except for D (which is clipped)
|
|
39
40
|
expect(editor.getCulledShapes()).toStrictEqual(new Set([ids.A, ids.B, ids.C]))
|
|
40
41
|
|
package/src/test/groups.test.tsx
CHANGED
|
@@ -1070,7 +1070,7 @@ describe('the select tool', () => {
|
|
|
1070
1070
|
// that we're doing hit testing manually—we'll catch that it was inside a shape
|
|
1071
1071
|
|
|
1072
1072
|
// editor.keyUp('Shift')
|
|
1073
|
-
//
|
|
1073
|
+
// vi.advanceTimersByTime(200)
|
|
1074
1074
|
|
|
1075
1075
|
// expect(editor.selectedShapeIds.includes(ids.boxA)).toBe(false)
|
|
1076
1076
|
// expect(editor.selectedShapeIds.includes(ids.boxB)).toBe(true)
|
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
import { PageRecordType, TLDeepLink, createDeepLinkString, createShapeId } from '@tldraw/editor'
|
|
2
|
+
import { vi } from 'vitest'
|
|
2
3
|
import { TestEditor } from './TestEditor'
|
|
3
4
|
import { TL } from './test-jsx'
|
|
4
5
|
|
|
5
|
-
|
|
6
|
+
vi.useFakeTimers()
|
|
6
7
|
|
|
7
8
|
let editor: TestEditor
|
|
8
9
|
|