You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
fix(editor): respect canReceiveNewChildrenOfType when dragging shapes (tldraw#8777)
In order to make container acceptance rules apply consistently during
pointer drag (not only on paste or create), this PR filters drag targets
and drag callback arguments using `canReceiveNewChildrenOfType` when
shape utils override it, and fixes the geometric reparent helper to
consider child types when picking candidate parents.
### Change type
- [x] `bugfix`
### Test plan
1. Override `canReceiveNewChildrenOfType` on a frame-like or container
shape to reject a type (e.g. `geo`).
2. Drag a shape of that type over the container; it should not reparent
until release, and should stay on the page when dropped.
3. Drag an accepted type; behavior should match prior frame drag-in
behavior.
4. Run `yarn test run src/test/frames.test.ts` in `packages/tldraw`.
- [x] Unit tests
- [ ] End to end tests
### Release notes
- Fix drag-and-drop so shapes that override
`canReceiveNewChildrenOfType` reject disallowed child types during drag,
not only on paste or create.
### Code changes
| Area | Description | Additions | Deletions |
| --- | --- | ---: | ---: |
| `packages/editor` | `getDraggingOverShape` skips targets that reject
all dragged types | 9 | 0 |
| `packages/editor` | `getDroppedShapesToNewParents` parent prefilter by
child types | 11 | 5 |
| `packages/tldraw` | `DragAndDropManager` filters shapes passed to drag
callbacks | 62 | 23 |
| `packages/tldraw` | Frame regression test for rejecting util | 34 | 0
|
| **Total** | | **116** | **28** |
Made with [Cursor](https://cursor.com)
### API changes
- adds `canRemoveChildrenOfType` for frame-like shapes
---------
Co-authored-by: Cursor <cursoragent@cursor.com>
Co-authored-by: Mime Čuvalo <mimecuvalo@gmail.com>
Copy file name to clipboardExpand all lines: apps/docs/content/releases/next.mdx
+1-1Lines changed: 1 addition & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -298,7 +298,7 @@ class AudioAssetUtil extends AssetUtil<TLAudioAsset> {
298
298
299
299
Customshapescannowoptintoframe-likebehavior: clippingchildren, acting asaparentonpasteanddrag-in, blocking erasure from inside, and supporting full-brush selection. Previously, frame behavior was hardcoded to the built-in `frame` type; the editor and tools now route frame checks through `editor.getShapeUtil(shape).isFrameLike(shape)`.
300
300
301
-
The easiest way to build one is to extend the new `BaseFrameLikeShapeUtil` abstract class, which provides sensible defaults for `isFrameLike`, `providesBackgroundForChildren`, `canReceiveNewChildrenOfType`, `getClipPath`, `onDragShapesIn`, and `onDragShapesOut`:
301
+
The easiest way to build one is to extend the new `BaseFrameLikeShapeUtil` abstract class, which provides sensible defaults for `isFrameLike`, `providesBackgroundForChildren`, `canReceiveNewChildrenOfType`, `canRemoveChildrenOfType`, `getClipPath`, `onDragShapesIn`, and `onDragShapesOut`:
302
302
303
303
```tsx
304
304
import { BaseFrameLikeShapeUtil, SVGContainer } from '@tldraw/editor'
Copy file name to clipboardExpand all lines: apps/docs/content/sdk-features/drag-and-drop.mdx
+15-2Lines changed: 15 additions & 2 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -169,7 +169,7 @@ Only shapes that implement drag callbacks are considered as drop targets. If you
169
169
170
170
## Controlling which shapes can be dropped
171
171
172
-
Use the [ShapeUtil#canReceiveNewChildrenOfType](?) method to control which shape types your container accepts:
172
+
Use the [ShapeUtil#canReceiveNewChildrenOfType](?) method to control which shape types your container accepts. The editor uses it to decide whether `onDragShapesIn` and `onDropShapesOver` fire for a dragged shape:
You must check this yourself in your drag callbacks. The editor does not call it automatically.
181
+
The default is `false`, so any shape that should accept dropped children must override this method. `onDragShapesOver` is not gated by this method, which lets you provide visual feedback even when the target won't accept the drop.
182
+
183
+
## Controlling which shapes can be dragged out
184
+
185
+
Use the [ShapeUtil#canRemoveChildrenOfType](?) method to control which child shape types can be dragged out of your container. The editor uses it to decide whether `onDragShapesOut` fires for a child shape, and to decide whether the editor should automatically reparent a child that has moved outside its parent's geometry:
0 commit comments