Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support Dragging External Items #250

Open
rossmeredith opened this issue Apr 15, 2023 · 3 comments
Open

Support Dragging External Items #250

rossmeredith opened this issue Apr 15, 2023 · 3 comments
Assignees

Comments

@rossmeredith
Copy link

I attempted dragging an external item onto a controlled tree but it does not trigger the onDrop handler. I tried an external drag item both external and internal to the controlled environment but neither worked.

Can dragging items outside the controlled environment be supported? I can't think of any reason why this would be difficult to implement but then again I know nothing about the internals of this library haha. So I would expect the first parameter, to be undefined, since I'm in control of this, and the second parameter, would be based on logic already written I'm guessing.

@rossmeredith
Copy link
Author

Did I ask a dumb question? Still no response after two weeks ...

@lukasbach
Copy link
Owner

Hey, not at all, just didn't have the time to look into this yet.

With some workarounds, this is kinda achievable already by just adding custom drop handlers to tree items, this can be done pretty quickly with a custom interaction mode: https://codesandbox.io/s/react-complex-tree-external-dragging-fkf88e?file=/src/App.tsx

It's probably not quite everything you want, since it doesn't show any drag effects, but maybe it's a good-enough workaround for you for now.

Right now, RCT internally keeps track of the drag state (list of dragging items and drag position), so to implement this feature properly, I could imagine using an empty list for dragging items for cases where custom elements are dragged in. The drop handler provided by the consumer is called in

const onDropHandler = useStableHandler(() => {
if (draggingItems && draggingPosition && environment.onDrop) {
environment.onDrop(draggingItems, draggingPosition);
callSoon(() => {
environment.onFocusItem?.(draggingItems[0], draggingPosition.treeId);
resetState();
});
}
});

so I suppose only the onFocusItem call would have to be adjusted to not fire. However, RCT also needs to be informed that a drag has started, so it can react to the drag event. Since this starts outside of RCT, the only good way I can think of, is doing that through an imperative ref on the environment. If there are better suggestions, I'm open. Right now, this is possible through [treeEnvRef.current.dragAndDropContext.onStartDraggingItems(items, treeId). But since this would become a consumer-oriented feature, a more convenient interface should probably be pulled up from the dragAndDropContext subprop to the environment ref, maybe something like treeEnvRef.current.startCustomDrag(treeId: string).

I haven't tested this, so not completely sure if this works how I imagine it right now. I'm open for other suggestions for how the interface could look like, and also contributions if anyone is interested.

@rossmeredith
Copy link
Author

Hi. Thanks for getting back to me. I'll look into what you suggest some time this week.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants