UNPKG

strapi-plugin-preview-button

Version:

A plugin for Strapi CMS that adds a preview button and live view button to the content manager edit view.

1,175 lines (1,174 loc) 33.8 kB
"use strict"; const React = require("react"); const index = require("./index-CSWOFhNV.js"); const clone = require("lodash/clone"); const toPath = require("lodash/toPath"); const _interopDefault = (e) => e && e.__esModule ? e : { default: e }; function _interopNamespace(e) { if (e && e.__esModule) return e; const n = Object.create(null, { [Symbol.toStringTag]: { value: "Module" } }); if (e) { for (const k in e) { if (k !== "default") { const d = Object.getOwnPropertyDescriptor(e, k); Object.defineProperty(n, k, d.get ? d : { enumerable: true, get: () => e[k] }); } } } n.default = e; return Object.freeze(n); } const React__namespace = /* @__PURE__ */ _interopNamespace(React); const clone__default = /* @__PURE__ */ _interopDefault(clone); const toPath__default = /* @__PURE__ */ _interopDefault(toPath); const DndContext = React.createContext({ dragDropManager: void 0 }); function invariant(condition, format, ...args) { if (isProduction()) { if (format === void 0) { throw new Error("invariant requires an error message argument"); } } if (!condition) { let error; if (format === void 0) { error = new Error("Minified exception occurred; use the non-minified dev environment for the full error message and additional helpful warnings."); } else { let argIndex = 0; error = new Error(format.replace(/%s/g, function() { return args[argIndex++]; })); error.name = "Invariant Violation"; } error.framesToPop = 1; throw error; } } function isProduction() { return typeof process !== "undefined" && process.env["NODE_ENV"] === "production"; } var fastDeepEqual = function equal(a, b) { if (a === b) return true; if (a && b && typeof a == "object" && typeof b == "object") { if (a.constructor !== b.constructor) return false; var length, i, keys; if (Array.isArray(a)) { length = a.length; if (length != b.length) return false; for (i = length; i-- !== 0; ) if (!equal(a[i], b[i])) return false; return true; } if (a.constructor === RegExp) return a.source === b.source && a.flags === b.flags; if (a.valueOf !== Object.prototype.valueOf) return a.valueOf() === b.valueOf(); if (a.toString !== Object.prototype.toString) return a.toString() === b.toString(); keys = Object.keys(a); length = keys.length; if (length !== Object.keys(b).length) return false; for (i = length; i-- !== 0; ) if (!Object.prototype.hasOwnProperty.call(b, keys[i])) return false; for (i = length; i-- !== 0; ) { var key = keys[i]; if (!equal(a[key], b[key])) return false; } return true; } return a !== a && b !== b; }; const equal2 = /* @__PURE__ */ index.getDefaultExportFromCjs(fastDeepEqual); const useIsomorphicLayoutEffect = typeof window !== "undefined" ? React.useLayoutEffect : React.useEffect; function useCollector(monitor, collect, onUpdate) { const [collected, setCollected] = React.useState( () => collect(monitor) ); const updateCollected = React.useCallback(() => { const nextValue = collect(monitor); if (!equal2(collected, nextValue)) { setCollected(nextValue); if (onUpdate) { onUpdate(); } } }, [ collected, monitor, onUpdate ]); useIsomorphicLayoutEffect(updateCollected); return [ collected, updateCollected ]; } function useMonitorOutput(monitor, collect, onCollect) { const [collected, updateCollected] = useCollector(monitor, collect, onCollect); useIsomorphicLayoutEffect(function subscribeToMonitorStateChange() { const handlerId = monitor.getHandlerId(); if (handlerId == null) { return; } return monitor.subscribeToStateChange(updateCollected, { handlerIds: [ handlerId ] }); }, [ monitor, updateCollected ]); return collected; } function useCollectedProps(collector, monitor, connector) { return useMonitorOutput( monitor, collector || (() => ({})), () => connector.reconnect() ); } function useOptionalFactory(arg, deps) { const memoDeps = [ ...[] ]; if (typeof arg !== "function") { memoDeps.push(arg); } return React.useMemo(() => { return typeof arg === "function" ? arg() : arg; }, memoDeps); } function useConnectDragSource(connector) { return React.useMemo( () => connector.hooks.dragSource(), [ connector ] ); } function useConnectDragPreview(connector) { return React.useMemo( () => connector.hooks.dragPreview(), [ connector ] ); } let isCallingCanDrag = false; let isCallingIsDragging = false; class DragSourceMonitorImpl { receiveHandlerId(sourceId) { this.sourceId = sourceId; } getHandlerId() { return this.sourceId; } canDrag() { invariant(!isCallingCanDrag, "You may not call monitor.canDrag() inside your canDrag() implementation. Read more: http://react-dnd.github.io/react-dnd/docs/api/drag-source-monitor"); try { isCallingCanDrag = true; return this.internalMonitor.canDragSource(this.sourceId); } finally { isCallingCanDrag = false; } } isDragging() { if (!this.sourceId) { return false; } invariant(!isCallingIsDragging, "You may not call monitor.isDragging() inside your isDragging() implementation. Read more: http://react-dnd.github.io/react-dnd/docs/api/drag-source-monitor"); try { isCallingIsDragging = true; return this.internalMonitor.isDraggingSource(this.sourceId); } finally { isCallingIsDragging = false; } } subscribeToStateChange(listener, options) { return this.internalMonitor.subscribeToStateChange(listener, options); } isDraggingSource(sourceId) { return this.internalMonitor.isDraggingSource(sourceId); } isOverTarget(targetId, options) { return this.internalMonitor.isOverTarget(targetId, options); } getTargetIds() { return this.internalMonitor.getTargetIds(); } isSourcePublic() { return this.internalMonitor.isSourcePublic(); } getSourceId() { return this.internalMonitor.getSourceId(); } subscribeToOffsetChange(listener) { return this.internalMonitor.subscribeToOffsetChange(listener); } canDragSource(sourceId) { return this.internalMonitor.canDragSource(sourceId); } canDropOnTarget(targetId) { return this.internalMonitor.canDropOnTarget(targetId); } getItemType() { return this.internalMonitor.getItemType(); } getItem() { return this.internalMonitor.getItem(); } getDropResult() { return this.internalMonitor.getDropResult(); } didDrop() { return this.internalMonitor.didDrop(); } getInitialClientOffset() { return this.internalMonitor.getInitialClientOffset(); } getInitialSourceClientOffset() { return this.internalMonitor.getInitialSourceClientOffset(); } getSourceClientOffset() { return this.internalMonitor.getSourceClientOffset(); } getClientOffset() { return this.internalMonitor.getClientOffset(); } getDifferenceFromInitialOffset() { return this.internalMonitor.getDifferenceFromInitialOffset(); } constructor(manager) { this.sourceId = null; this.internalMonitor = manager.getMonitor(); } } let isCallingCanDrop = false; class DropTargetMonitorImpl { receiveHandlerId(targetId) { this.targetId = targetId; } getHandlerId() { return this.targetId; } subscribeToStateChange(listener, options) { return this.internalMonitor.subscribeToStateChange(listener, options); } canDrop() { if (!this.targetId) { return false; } invariant(!isCallingCanDrop, "You may not call monitor.canDrop() inside your canDrop() implementation. Read more: http://react-dnd.github.io/react-dnd/docs/api/drop-target-monitor"); try { isCallingCanDrop = true; return this.internalMonitor.canDropOnTarget(this.targetId); } finally { isCallingCanDrop = false; } } isOver(options) { if (!this.targetId) { return false; } return this.internalMonitor.isOverTarget(this.targetId, options); } getItemType() { return this.internalMonitor.getItemType(); } getItem() { return this.internalMonitor.getItem(); } getDropResult() { return this.internalMonitor.getDropResult(); } didDrop() { return this.internalMonitor.didDrop(); } getInitialClientOffset() { return this.internalMonitor.getInitialClientOffset(); } getInitialSourceClientOffset() { return this.internalMonitor.getInitialSourceClientOffset(); } getSourceClientOffset() { return this.internalMonitor.getSourceClientOffset(); } getClientOffset() { return this.internalMonitor.getClientOffset(); } getDifferenceFromInitialOffset() { return this.internalMonitor.getDifferenceFromInitialOffset(); } constructor(manager) { this.targetId = null; this.internalMonitor = manager.getMonitor(); } } function registerTarget(type, target, manager) { const registry = manager.getRegistry(); const targetId = registry.addTarget(type, target); return [ targetId, () => registry.removeTarget(targetId) ]; } function registerSource(type, source, manager) { const registry = manager.getRegistry(); const sourceId = registry.addSource(type, source); return [ sourceId, () => registry.removeSource(sourceId) ]; } function shallowEqual(objA, objB, compare, compareContext) { let compareResult = void 0; if (compareResult !== void 0) { return !!compareResult; } if (objA === objB) { return true; } if (typeof objA !== "object" || !objA || typeof objB !== "object" || !objB) { return false; } const keysA = Object.keys(objA); const keysB = Object.keys(objB); if (keysA.length !== keysB.length) { return false; } const bHasOwnProperty = Object.prototype.hasOwnProperty.bind(objB); for (let idx = 0; idx < keysA.length; idx++) { const key = keysA[idx]; if (!bHasOwnProperty(key)) { return false; } const valueA = objA[key]; const valueB = objB[key]; compareResult = void 0; if (compareResult === false || compareResult === void 0 && valueA !== valueB) { return false; } } return true; } function isRef(obj) { return ( // eslint-disable-next-line no-prototype-builtins obj !== null && typeof obj === "object" && Object.prototype.hasOwnProperty.call(obj, "current") ); } function throwIfCompositeComponentElement(element) { if (typeof element.type === "string") { return; } const displayName = element.type.displayName || element.type.name || "the component"; throw new Error(`Only native element nodes can now be passed to React DnD connectors.You can either wrap ${displayName} into a <div>, or turn it into a drag source or a drop target itself.`); } function wrapHookToRecognizeElement(hook) { return (elementOrNode = null, options = null) => { if (!React.isValidElement(elementOrNode)) { const node = elementOrNode; hook(node, options); return node; } const element = elementOrNode; throwIfCompositeComponentElement(element); const ref = options ? (node) => hook(node, options) : hook; return cloneWithRef(element, ref); }; } function wrapConnectorHooks(hooks) { const wrappedHooks = {}; Object.keys(hooks).forEach((key) => { const hook = hooks[key]; if (key.endsWith("Ref")) { wrappedHooks[key] = hooks[key]; } else { const wrappedHook = wrapHookToRecognizeElement(hook); wrappedHooks[key] = () => wrappedHook; } }); return wrappedHooks; } function setRef(ref, node) { if (typeof ref === "function") { ref(node); } else { ref.current = node; } } function cloneWithRef(element, newRef) { const previousRef = element.ref; invariant(typeof previousRef !== "string", "Cannot connect React DnD to an element with an existing string ref. Please convert it to use a callback ref instead, or wrap it into a <span> or <div>. Read more: https://reactjs.org/docs/refs-and-the-dom.html#callback-refs"); if (!previousRef) { return React.cloneElement(element, { ref: newRef }); } else { return React.cloneElement(element, { ref: (node) => { setRef(previousRef, node); setRef(newRef, node); } }); } } class SourceConnector { receiveHandlerId(newHandlerId) { if (this.handlerId === newHandlerId) { return; } this.handlerId = newHandlerId; this.reconnect(); } get connectTarget() { return this.dragSource; } get dragSourceOptions() { return this.dragSourceOptionsInternal; } set dragSourceOptions(options) { this.dragSourceOptionsInternal = options; } get dragPreviewOptions() { return this.dragPreviewOptionsInternal; } set dragPreviewOptions(options) { this.dragPreviewOptionsInternal = options; } reconnect() { const didChange = this.reconnectDragSource(); this.reconnectDragPreview(didChange); } reconnectDragSource() { const dragSource = this.dragSource; const didChange = this.didHandlerIdChange() || this.didConnectedDragSourceChange() || this.didDragSourceOptionsChange(); if (didChange) { this.disconnectDragSource(); } if (!this.handlerId) { return didChange; } if (!dragSource) { this.lastConnectedDragSource = dragSource; return didChange; } if (didChange) { this.lastConnectedHandlerId = this.handlerId; this.lastConnectedDragSource = dragSource; this.lastConnectedDragSourceOptions = this.dragSourceOptions; this.dragSourceUnsubscribe = this.backend.connectDragSource(this.handlerId, dragSource, this.dragSourceOptions); } return didChange; } reconnectDragPreview(forceDidChange = false) { const dragPreview = this.dragPreview; const didChange = forceDidChange || this.didHandlerIdChange() || this.didConnectedDragPreviewChange() || this.didDragPreviewOptionsChange(); if (didChange) { this.disconnectDragPreview(); } if (!this.handlerId) { return; } if (!dragPreview) { this.lastConnectedDragPreview = dragPreview; return; } if (didChange) { this.lastConnectedHandlerId = this.handlerId; this.lastConnectedDragPreview = dragPreview; this.lastConnectedDragPreviewOptions = this.dragPreviewOptions; this.dragPreviewUnsubscribe = this.backend.connectDragPreview(this.handlerId, dragPreview, this.dragPreviewOptions); } } didHandlerIdChange() { return this.lastConnectedHandlerId !== this.handlerId; } didConnectedDragSourceChange() { return this.lastConnectedDragSource !== this.dragSource; } didConnectedDragPreviewChange() { return this.lastConnectedDragPreview !== this.dragPreview; } didDragSourceOptionsChange() { return !shallowEqual(this.lastConnectedDragSourceOptions, this.dragSourceOptions); } didDragPreviewOptionsChange() { return !shallowEqual(this.lastConnectedDragPreviewOptions, this.dragPreviewOptions); } disconnectDragSource() { if (this.dragSourceUnsubscribe) { this.dragSourceUnsubscribe(); this.dragSourceUnsubscribe = void 0; } } disconnectDragPreview() { if (this.dragPreviewUnsubscribe) { this.dragPreviewUnsubscribe(); this.dragPreviewUnsubscribe = void 0; this.dragPreviewNode = null; this.dragPreviewRef = null; } } get dragSource() { return this.dragSourceNode || this.dragSourceRef && this.dragSourceRef.current; } get dragPreview() { return this.dragPreviewNode || this.dragPreviewRef && this.dragPreviewRef.current; } clearDragSource() { this.dragSourceNode = null; this.dragSourceRef = null; } clearDragPreview() { this.dragPreviewNode = null; this.dragPreviewRef = null; } constructor(backend) { this.hooks = wrapConnectorHooks({ dragSource: (node, options) => { this.clearDragSource(); this.dragSourceOptions = options || null; if (isRef(node)) { this.dragSourceRef = node; } else { this.dragSourceNode = node; } this.reconnectDragSource(); }, dragPreview: (node, options) => { this.clearDragPreview(); this.dragPreviewOptions = options || null; if (isRef(node)) { this.dragPreviewRef = node; } else { this.dragPreviewNode = node; } this.reconnectDragPreview(); } }); this.handlerId = null; this.dragSourceRef = null; this.dragSourceOptionsInternal = null; this.dragPreviewRef = null; this.dragPreviewOptionsInternal = null; this.lastConnectedHandlerId = null; this.lastConnectedDragSource = null; this.lastConnectedDragSourceOptions = null; this.lastConnectedDragPreview = null; this.lastConnectedDragPreviewOptions = null; this.backend = backend; } } class TargetConnector { get connectTarget() { return this.dropTarget; } reconnect() { const didChange = this.didHandlerIdChange() || this.didDropTargetChange() || this.didOptionsChange(); if (didChange) { this.disconnectDropTarget(); } const dropTarget = this.dropTarget; if (!this.handlerId) { return; } if (!dropTarget) { this.lastConnectedDropTarget = dropTarget; return; } if (didChange) { this.lastConnectedHandlerId = this.handlerId; this.lastConnectedDropTarget = dropTarget; this.lastConnectedDropTargetOptions = this.dropTargetOptions; this.unsubscribeDropTarget = this.backend.connectDropTarget(this.handlerId, dropTarget, this.dropTargetOptions); } } receiveHandlerId(newHandlerId) { if (newHandlerId === this.handlerId) { return; } this.handlerId = newHandlerId; this.reconnect(); } get dropTargetOptions() { return this.dropTargetOptionsInternal; } set dropTargetOptions(options) { this.dropTargetOptionsInternal = options; } didHandlerIdChange() { return this.lastConnectedHandlerId !== this.handlerId; } didDropTargetChange() { return this.lastConnectedDropTarget !== this.dropTarget; } didOptionsChange() { return !shallowEqual(this.lastConnectedDropTargetOptions, this.dropTargetOptions); } disconnectDropTarget() { if (this.unsubscribeDropTarget) { this.unsubscribeDropTarget(); this.unsubscribeDropTarget = void 0; } } get dropTarget() { return this.dropTargetNode || this.dropTargetRef && this.dropTargetRef.current; } clearDropTarget() { this.dropTargetRef = null; this.dropTargetNode = null; } constructor(backend) { this.hooks = wrapConnectorHooks({ dropTarget: (node, options) => { this.clearDropTarget(); this.dropTargetOptions = options; if (isRef(node)) { this.dropTargetRef = node; } else { this.dropTargetNode = node; } this.reconnect(); } }); this.handlerId = null; this.dropTargetRef = null; this.dropTargetOptionsInternal = null; this.lastConnectedHandlerId = null; this.lastConnectedDropTarget = null; this.lastConnectedDropTargetOptions = null; this.backend = backend; } } function useDragDropManager() { const { dragDropManager } = React.useContext(DndContext); invariant(dragDropManager != null, "Expected drag drop context"); return dragDropManager; } function useDragSourceConnector(dragSourceOptions, dragPreviewOptions) { const manager = useDragDropManager(); const connector = React.useMemo( () => new SourceConnector(manager.getBackend()), [ manager ] ); useIsomorphicLayoutEffect(() => { connector.dragSourceOptions = dragSourceOptions || null; connector.reconnect(); return () => connector.disconnectDragSource(); }, [ connector, dragSourceOptions ]); useIsomorphicLayoutEffect(() => { connector.dragPreviewOptions = dragPreviewOptions || null; connector.reconnect(); return () => connector.disconnectDragPreview(); }, [ connector, dragPreviewOptions ]); return connector; } function useDragSourceMonitor() { const manager = useDragDropManager(); return React.useMemo( () => new DragSourceMonitorImpl(manager), [ manager ] ); } class DragSourceImpl { beginDrag() { const spec = this.spec; const monitor = this.monitor; let result = null; if (typeof spec.item === "object") { result = spec.item; } else if (typeof spec.item === "function") { result = spec.item(monitor); } else { result = {}; } return result !== null && result !== void 0 ? result : null; } canDrag() { const spec = this.spec; const monitor = this.monitor; if (typeof spec.canDrag === "boolean") { return spec.canDrag; } else if (typeof spec.canDrag === "function") { return spec.canDrag(monitor); } else { return true; } } isDragging(globalMonitor, target) { const spec = this.spec; const monitor = this.monitor; const { isDragging } = spec; return isDragging ? isDragging(monitor) : target === globalMonitor.getSourceId(); } endDrag() { const spec = this.spec; const monitor = this.monitor; const connector = this.connector; const { end } = spec; if (end) { end(monitor.getItem(), monitor); } connector.reconnect(); } constructor(spec, monitor, connector) { this.spec = spec; this.monitor = monitor; this.connector = connector; } } function useDragSource(spec, monitor, connector) { const handler = React.useMemo( () => new DragSourceImpl(spec, monitor, connector), [ monitor, connector ] ); React.useEffect(() => { handler.spec = spec; }, [ spec ]); return handler; } function useDragType(spec) { return React.useMemo(() => { const result = spec.type; invariant(result != null, "spec.type must be defined"); return result; }, [ spec ]); } function useRegisteredDragSource(spec, monitor, connector) { const manager = useDragDropManager(); const handler = useDragSource(spec, monitor, connector); const itemType = useDragType(spec); useIsomorphicLayoutEffect(function registerDragSource() { if (itemType != null) { const [handlerId, unregister] = registerSource(itemType, handler, manager); monitor.receiveHandlerId(handlerId); connector.receiveHandlerId(handlerId); return unregister; } return; }, [ manager, monitor, connector, handler, itemType ]); } function useDrag(specArg, deps) { const spec = useOptionalFactory(specArg); invariant(!spec.begin, `useDrag::spec.begin was deprecated in v14. Replace spec.begin() with spec.item(). (see more here - https://react-dnd.github.io/react-dnd/docs/api/use-drag)`); const monitor = useDragSourceMonitor(); const connector = useDragSourceConnector(spec.options, spec.previewOptions); useRegisteredDragSource(spec, monitor, connector); return [ useCollectedProps(spec.collect, monitor, connector), useConnectDragSource(connector), useConnectDragPreview(connector) ]; } function useConnectDropTarget(connector) { return React.useMemo( () => connector.hooks.dropTarget(), [ connector ] ); } function useDropTargetConnector(options) { const manager = useDragDropManager(); const connector = React.useMemo( () => new TargetConnector(manager.getBackend()), [ manager ] ); useIsomorphicLayoutEffect(() => { connector.dropTargetOptions = options || null; connector.reconnect(); return () => connector.disconnectDropTarget(); }, [ options ]); return connector; } function useDropTargetMonitor() { const manager = useDragDropManager(); return React.useMemo( () => new DropTargetMonitorImpl(manager), [ manager ] ); } function useAccept(spec) { const { accept } = spec; return React.useMemo(() => { invariant(spec.accept != null, "accept must be defined"); return Array.isArray(accept) ? accept : [ accept ]; }, [ accept ]); } class DropTargetImpl { canDrop() { const spec = this.spec; const monitor = this.monitor; return spec.canDrop ? spec.canDrop(monitor.getItem(), monitor) : true; } hover() { const spec = this.spec; const monitor = this.monitor; if (spec.hover) { spec.hover(monitor.getItem(), monitor); } } drop() { const spec = this.spec; const monitor = this.monitor; if (spec.drop) { return spec.drop(monitor.getItem(), monitor); } return; } constructor(spec, monitor) { this.spec = spec; this.monitor = monitor; } } function useDropTarget(spec, monitor) { const dropTarget = React.useMemo( () => new DropTargetImpl(spec, monitor), [ monitor ] ); React.useEffect(() => { dropTarget.spec = spec; }, [ spec ]); return dropTarget; } function useRegisteredDropTarget(spec, monitor, connector) { const manager = useDragDropManager(); const dropTarget = useDropTarget(spec, monitor); const accept = useAccept(spec); useIsomorphicLayoutEffect(function registerDropTarget() { const [handlerId, unregister] = registerTarget(accept, dropTarget, manager); monitor.receiveHandlerId(handlerId); connector.receiveHandlerId(handlerId); return unregister; }, [ manager, monitor, dropTarget, connector, accept.map( (a) => a.toString() ).join("|") ]); } function useDrop(specArg, deps) { const spec = useOptionalFactory(specArg); const monitor = useDropTargetMonitor(); const connector = useDropTargetConnector(spec.options); useRegisteredDropTarget(spec, monitor, connector); return [ useCollectedProps(spec.collect, monitor, connector), useConnectDropTarget(connector) ]; } let emptyImage; function getEmptyImage() { if (!emptyImage) { emptyImage = new Image(); emptyImage.src = "data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw=="; } return emptyImage; } const ItemTypes = { COMPONENT: "component", EDIT_FIELD: "editField", FIELD: "field", DYNAMIC_ZONE: "dynamicZone", RELATION: "relation", BLOCKS: "blocks" }; const useKeyboardDragAndDrop = (active, index2, { onCancel, onDropItem, onGrabItem, onMoveItem }) => { const [isSelected, setIsSelected] = React__namespace.useState(false); const handleMove = (movement) => { if (!isSelected) { return; } if (typeof index2 === "number" && onMoveItem) { if (movement === "UP") { onMoveItem(index2 - 1, index2); } else if (movement === "DOWN") { onMoveItem(index2 + 1, index2); } } }; const handleDragClick = () => { if (isSelected) { if (onDropItem) { onDropItem(index2); } setIsSelected(false); } else { if (onGrabItem) { onGrabItem(index2); } setIsSelected(true); } }; const handleCancel = () => { if (isSelected) { setIsSelected(false); if (onCancel) { onCancel(index2); } } }; const handleKeyDown = (e) => { if (!active) { return; } if (e.key === "Tab" && !isSelected) { return; } e.preventDefault(); switch (e.key) { case " ": case "Enter": handleDragClick(); break; case "Escape": handleCancel(); break; case "ArrowDown": case "ArrowRight": handleMove("DOWN"); break; case "ArrowUp": case "ArrowLeft": handleMove("UP"); break; } }; return handleKeyDown; }; const DIRECTIONS = { UPWARD: "upward", DOWNWARD: "downward" }; const DROP_SENSITIVITY = { REGULAR: "regular", IMMEDIATE: "immediate" }; const useDragAndDrop = (active, { type = "STRAPI_DND", index: index2, item, onStart, onEnd, onGrabItem, onDropItem, onCancel, onMoveItem, dropSensitivity = DROP_SENSITIVITY.REGULAR }) => { const objectRef = React__namespace.useRef(null); const [{ handlerId, isOver }, dropRef] = useDrop({ accept: type, collect(monitor) { return { handlerId: monitor.getHandlerId(), isOver: monitor.isOver({ shallow: true }) }; }, drop(item2) { const draggedIndex = item2.index; const newIndex = index2; if (isOver && onDropItem) { onDropItem(draggedIndex, newIndex); } }, hover(item2, monitor) { if (!objectRef.current || !onMoveItem) { return; } const dragIndex = item2.index; const newIndex = index2; const hoverBoundingRect = objectRef.current?.getBoundingClientRect(); const hoverMiddleY = (hoverBoundingRect.bottom - hoverBoundingRect.top) / 2; const clientOffset = monitor.getClientOffset(); if (!clientOffset) return; const hoverClientY = clientOffset && clientOffset.y - hoverBoundingRect.top; if (typeof dragIndex === "number" && typeof newIndex === "number") { if (dragIndex === newIndex) { return; } if (dropSensitivity === DROP_SENSITIVITY.REGULAR) { if (dragIndex < newIndex && hoverClientY < hoverMiddleY) { return; } if (dragIndex > newIndex && hoverClientY > hoverMiddleY) { return; } } onMoveItem(newIndex, dragIndex); item2.index = newIndex; } else { if (Array.isArray(dragIndex) && Array.isArray(newIndex)) { const minLength = Math.min(dragIndex.length, newIndex.length); let areEqual = true; let isLessThan = false; let isGreaterThan = false; for (let i = 0; i < minLength; i++) { if (dragIndex[i] < newIndex[i]) { isLessThan = true; areEqual = false; break; } else if (dragIndex[i] > newIndex[i]) { isGreaterThan = true; areEqual = false; break; } } if (areEqual && dragIndex.length === newIndex.length) { return; } if (dropSensitivity === DROP_SENSITIVITY.REGULAR) { if (isLessThan && !isGreaterThan && hoverClientY < hoverMiddleY) { return; } if (isGreaterThan && !isLessThan && hoverClientY > hoverMiddleY) { return; } } } onMoveItem(newIndex, dragIndex); item2.index = newIndex; } } }); const getDragDirection = (monitor) => { if (monitor && monitor.isDragging() && !monitor.didDrop() && monitor.getInitialClientOffset() && monitor.getClientOffset()) { const deltaY = monitor.getInitialClientOffset().y - monitor.getClientOffset().y; if (deltaY > 0) return DIRECTIONS.UPWARD; if (deltaY < 0) return DIRECTIONS.DOWNWARD; return null; } return null; }; const [{ isDragging, direction }, dragRef, dragPreviewRef] = useDrag({ type, item() { if (onStart) { onStart(); } const { width } = objectRef.current?.getBoundingClientRect() ?? {}; return { index: index2, width, ...item }; }, end() { if (onEnd) { onEnd(); } }, canDrag: active, /** * This is useful when the item is in a virtualized list. * However, if we don't have an ID then we want the libraries * defaults to take care of this. */ isDragging: item?.id ? (monitor) => { return item.id === monitor.getItem().id; } : void 0, collect: (monitor) => ({ isDragging: monitor.isDragging(), initialOffset: monitor.getInitialClientOffset(), currentOffset: monitor.getClientOffset(), direction: getDragDirection(monitor) }) }); const handleKeyDown = useKeyboardDragAndDrop(active, index2, { onGrabItem, onDropItem, onCancel, onMoveItem }); return [ { handlerId, isDragging, handleKeyDown, isOverDropTarget: isOver, direction }, objectRef, dropRef, dragRef, dragPreviewRef ]; }; function getIn(obj, key, def, pathStartIndex = 0) { const path = toPath__default.default(key); while (obj && pathStartIndex < path.length) { obj = obj[path[pathStartIndex++]]; } if (pathStartIndex !== path.length && !obj) { return def; } return obj === void 0 ? def : obj; } const isObject = (obj) => obj !== null && typeof obj === "object" && !Array.isArray(obj); const isInteger = (obj) => String(Math.floor(Number(obj))) === obj; function setIn(obj, path, value) { const res = clone__default.default(obj); let resVal = res; let i = 0; const pathArray = toPath__default.default(path); for (; i < pathArray.length - 1; i++) { const currentPath = pathArray[i]; const currentObj = getIn(obj, pathArray.slice(0, i + 1)); if (currentObj && (isObject(currentObj) || Array.isArray(currentObj))) { resVal = resVal[currentPath] = clone__default.default(currentObj); } else { const nextPath = pathArray[i + 1]; resVal = resVal[currentPath] = isInteger(nextPath) && Number(nextPath) >= 0 ? [] : {}; } } if ((i === 0 ? obj : resVal)[pathArray[i]] === value) { return obj; } { delete resVal[pathArray[i]]; } if (i === 0 && value === void 0) { delete res[pathArray[i]]; } return res; } exports.DIRECTIONS = DIRECTIONS; exports.DROP_SENSITIVITY = DROP_SENSITIVITY; exports.ItemTypes = ItemTypes; exports.getEmptyImage = getEmptyImage; exports.getIn = getIn; exports.setIn = setIn; exports.useDragAndDrop = useDragAndDrop;