UNPKG

@atlaskit/pragmatic-drag-and-drop-react-beautiful-dnd-migration

Version:

An optional Pragmatic drag and drop package that enables rapid migration from react-beautiful-dnd to Pragmatic drag and drop

222 lines (211 loc) 6.95 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.getIndicatorSizeAndOffset = getIndicatorSizeAndOffset; var _attributes = require("../../utils/attributes"); var _findClosestScrollContainer = require("../../utils/find-closest-scroll-container"); var _findElement = require("../../utils/find-element"); var _findPlaceholder = require("../../utils/find-placeholder"); var _getClosestPositionedElement = require("../../utils/get-closest-positioned-element"); var _getElementByDraggableLocation = require("../../utils/get-element-by-draggable-location"); var _gap = require("../gap"); var _constants = require("./constants"); // eslint-disable-next-line import/no-extraneous-dependencies /** * Returns the dimensions for a drop indicator either before or after a * draggable. * * `isForwardEdge` determines whether it is before or after. */ function measureDraggable(_ref) { var element = _ref.element, isForwardEdge = _ref.isForwardEdge, mode = _ref.mode, direction = _ref.direction, contextId = _ref.contextId; var _directionMapping$dir = _constants.directionMapping[direction], mainAxis = _directionMapping$dir.mainAxis, crossAxis = _directionMapping$dir.crossAxis; var offsetElement = (0, _getClosestPositionedElement.getClosestPositionedElement)({ element: element, mode: mode }); var gapOffset = (0, _gap.getGapOffset)({ element: element, where: isForwardEdge ? 'after' : 'before', direction: direction, contextId: contextId }); var baseOffset = offsetElement[mainAxis.offset] - _constants.lineOffset; var mainAxisOffset = isForwardEdge ? baseOffset + element[mainAxis.length] : baseOffset; return { mainAxis: { offset: mainAxisOffset + gapOffset }, crossAxis: { offset: offsetElement[crossAxis.offset], length: offsetElement[crossAxis.length] } }; } /** * This will return an indicator size and offset corresponding to a line * through the middle of the placeholder. * * The reason this is a special case, instead of just falling back to the * standard positioning logic, is to avoid measuring the drag preview. */ function measurePlaceholder(_ref2) { var element = _ref2.element, direction = _ref2.direction; var _directionMapping$dir2 = _constants.directionMapping[direction], mainAxis = _directionMapping$dir2.mainAxis, crossAxis = _directionMapping$dir2.crossAxis; /** * This function measures against the `element` directly instead of an * `offsetElement` because: * - For standard lists, that is already the behavior. * - For virtual lists, we know that the `element` is being absolutely * positioned (and not an ancestor). */ var baseOffset = element[mainAxis.offset] - _constants.lineOffset; var mainAxisOffset = baseOffset + element[mainAxis.length] / 2; return { mainAxis: { offset: mainAxisOffset }, crossAxis: { offset: element[crossAxis.offset], length: element[crossAxis.length] } }; } function getDroppableOffset(_ref3) { var element = _ref3.element, direction = _ref3.direction; var mainAxis = _constants.directionMapping[direction].mainAxis; var scrollContainer = (0, _findClosestScrollContainer.findClosestScrollContainer)(element); if (!scrollContainer) { return 0; } /** * If the scroll container has static positioning, * then we need to add the scroll container's offset as well. */ var _getComputedStyle = getComputedStyle(scrollContainer), position = _getComputedStyle.position; if (position !== 'static') { return 0; } return scrollContainer[mainAxis.offset]; } /** * Returns the dimensions for a drop indicator in an empty list. */ function measureDroppable(_ref4) { var droppableId = _ref4.droppableId, direction = _ref4.direction; var element = (0, _findElement.getElement)({ attribute: _attributes.attributes.droppable.id, value: droppableId }); var mainAxisOffset = getDroppableOffset({ element: element, direction: direction }); return { mainAxis: { offset: mainAxisOffset }, crossAxis: { offset: 0, length: '100%' } }; } function getIndicatorSizeAndOffset(_ref5) { var targetLocation = _ref5.targetLocation, isInHomeLocation = _ref5.isInHomeLocation, direction = _ref5.direction, mode = _ref5.mode, contextId = _ref5.contextId; if (isInHomeLocation) { /** * If we are in the home location (source === destination) then the * indicator is centered in the placeholder. * * It isn't visible, but is used to scroll to. * * This is a special case, because the standard logic will not work * correctly when measuring the drag preview, * which occurs when in the home location. * * This is because the drag preview: * * 1. Has `position: fixed; top: 0; left: 0;` so its `offsetTop` and `offsetLeft` * will always be `0`, which result in the indicator being at the start of the list. * 2. Is in the wrong location anyway. * * `measurePlaceholder()` is specifically designed for this case. */ var _element = (0, _findPlaceholder.findPlaceholder)(contextId); if (!_element) { return null; } return measurePlaceholder({ element: _element, direction: direction }); } if (targetLocation.index === 0) { /** * If the target is the 0th index, there are two situations: * * 1. Targeting an empty list * 2. Targeting before the first item in the list */ var _element2 = (0, _getElementByDraggableLocation.getElementByDraggableLocation)(contextId, targetLocation); if (!_element2) { /** * If there's no element in the location, it is because the list is empty. * In this case, we measure the droppable itself to draw the indicator. */ return measureDroppable({ droppableId: targetLocation.droppableId, direction: direction }); } /** * Otherwise, there is a reference element we can use to measure. */ return measureDraggable({ element: _element2, // `false` because the line is before the item isForwardEdge: false, mode: mode, direction: direction, contextId: contextId }); } /** * Otherwise, for any other index, we can measure the draggable above where * we would be dropping. */ var element = (0, _getElementByDraggableLocation.getElementByDraggableLocation)(contextId, { droppableId: targetLocation.droppableId, // subtracting one because it is the draggable above index: targetLocation.index - 1 }); if (!element) { return null; } return measureDraggable({ element: element, // `true` because the line is after the item isForwardEdge: true, mode: mode, direction: direction, contextId: contextId }); }