81 lines
2.4 KiB
TypeScript
81 lines
2.4 KiB
TypeScript
import { useEffect } from 'react';
|
|
import type { MutableRefObject } from 'react';
|
|
import {
|
|
isTagTransferEvent,
|
|
getActiveDragState,
|
|
} from '../features/tagging/tagTransfer';
|
|
|
|
interface UseWorkspaceDragDropArgs {
|
|
shellRef: MutableRefObject<HTMLElement | null>;
|
|
}
|
|
|
|
const useWorkspaceDragDrop = ({
|
|
shellRef,
|
|
}: UseWorkspaceDragDropArgs) => {
|
|
|
|
useEffect(() => {
|
|
const host = shellRef.current;
|
|
if (!host) {
|
|
return;
|
|
}
|
|
|
|
// Allow drop on workspace (global app shell)
|
|
const handleTagDragOver = (event: DragEvent) => {
|
|
if (!isTagTransferEvent(event)) {
|
|
return;
|
|
}
|
|
|
|
const { sourceDocId } = getActiveDragState();
|
|
|
|
// Only allow "Move" (removal) if the tag came from a document
|
|
if (sourceDocId) {
|
|
event.preventDefault(); // Necessary to allow dropping
|
|
if (event.dataTransfer) {
|
|
event.dataTransfer.dropEffect = 'move';
|
|
}
|
|
}
|
|
};
|
|
|
|
const handleTagDragEnter = (event: DragEvent) => {
|
|
if (!isTagTransferEvent(event)) {
|
|
return;
|
|
}
|
|
const { sourceDocId } = getActiveDragState();
|
|
if (sourceDocId) {
|
|
event.preventDefault();
|
|
if (event.dataTransfer) {
|
|
event.dataTransfer.dropEffect = 'move';
|
|
}
|
|
}
|
|
};
|
|
|
|
const handleTagDrop = (event: DragEvent) => {
|
|
if (!isTagTransferEvent(event)) {
|
|
return;
|
|
}
|
|
|
|
const { sourceDocId } = getActiveDragState();
|
|
|
|
if (sourceDocId) {
|
|
// Consume the event so the browser reports 'move' back to the source
|
|
event.preventDefault();
|
|
}
|
|
};
|
|
|
|
// Use bubbling (false) so children can stopPropagation
|
|
host.addEventListener('dragenter', handleTagDragEnter, false);
|
|
host.addEventListener('dragover', handleTagDragOver, false);
|
|
host.addEventListener('drop', handleTagDrop, false);
|
|
|
|
return () => {
|
|
host.removeEventListener('dragenter', handleTagDragEnter, false);
|
|
host.removeEventListener('dragover', handleTagDragOver, false);
|
|
host.removeEventListener('drop', handleTagDrop, false);
|
|
};
|
|
}, [shellRef]);
|
|
|
|
return {};
|
|
};
|
|
|
|
export default useWorkspaceDragDrop;
|