UNPKG

ahooks

Version:
86 lines (85 loc) 3.76 kB
import useLatest from '../useLatest'; import { getTargetElement } from '../utils/domTarget'; import useEffectWithTarget from '../utils/useEffectWithTarget'; import { useRef } from 'react'; const useDrop = (target, options = {}) => { const optionsRef = useLatest(options); // https://stackoverflow.com/a/26459269 const dragEnterTarget = useRef(undefined); useEffectWithTarget(() => { const targetElement = getTargetElement(target); if (!(targetElement === null || targetElement === void 0 ? void 0 : targetElement.addEventListener)) { return; } const onData = (dataTransfer, event) => { const uri = dataTransfer.getData('text/uri-list'); const dom = dataTransfer.getData('custom'); if (dom && optionsRef.current.onDom) { let data = dom; try { data = JSON.parse(dom); } catch (_a) { data = dom; } optionsRef.current.onDom(data, event); return; } if (uri && optionsRef.current.onUri) { optionsRef.current.onUri(uri, event); return; } if (dataTransfer.files && dataTransfer.files.length && optionsRef.current.onFiles) { optionsRef.current.onFiles(Array.from(dataTransfer.files), event); return; } if (dataTransfer.items && dataTransfer.items.length && optionsRef.current.onText) { dataTransfer.items[0].getAsString((text) => { optionsRef.current.onText(text, event); }); } }; const onDragEnter = (event) => { var _a, _b; event.preventDefault(); event.stopPropagation(); dragEnterTarget.current = event.target; (_b = (_a = optionsRef.current).onDragEnter) === null || _b === void 0 ? void 0 : _b.call(_a, event); }; const onDragOver = (event) => { var _a, _b; event.preventDefault(); (_b = (_a = optionsRef.current).onDragOver) === null || _b === void 0 ? void 0 : _b.call(_a, event); }; const onDragLeave = (event) => { var _a, _b; if (event.target === dragEnterTarget.current) { (_b = (_a = optionsRef.current).onDragLeave) === null || _b === void 0 ? void 0 : _b.call(_a, event); } }; const onDrop = (event) => { var _a, _b; event.preventDefault(); onData(event.dataTransfer, event); (_b = (_a = optionsRef.current).onDrop) === null || _b === void 0 ? void 0 : _b.call(_a, event); }; const onPaste = (event) => { var _a, _b; onData(event.clipboardData, event); (_b = (_a = optionsRef.current).onPaste) === null || _b === void 0 ? void 0 : _b.call(_a, event); }; targetElement.addEventListener('dragenter', onDragEnter); targetElement.addEventListener('dragover', onDragOver); targetElement.addEventListener('dragleave', onDragLeave); targetElement.addEventListener('drop', onDrop); targetElement.addEventListener('paste', onPaste); return () => { targetElement.removeEventListener('dragenter', onDragEnter); targetElement.removeEventListener('dragover', onDragOver); targetElement.removeEventListener('dragleave', onDragLeave); targetElement.removeEventListener('drop', onDrop); targetElement.removeEventListener('paste', onPaste); }; }, [], target); }; export default useDrop;