147 lines
4.8 KiB
JavaScript
147 lines
4.8 KiB
JavaScript
|
import getOppositePlacement from "../utils/getOppositePlacement.js";
|
|||
|
import getBasePlacement from "../utils/getBasePlacement.js";
|
|||
|
import getOppositeVariationPlacement from "../utils/getOppositeVariationPlacement.js";
|
|||
|
import detectOverflow from "../utils/detectOverflow.js";
|
|||
|
import computeAutoPlacement from "../utils/computeAutoPlacement.js";
|
|||
|
import { bottom, top, start, right, left, auto } from "../enums.js";
|
|||
|
import getVariation from "../utils/getVariation.js"; // eslint-disable-next-line import/no-unused-modules
|
|||
|
|
|||
|
function getExpandedFallbackPlacements(placement) {
|
|||
|
if (getBasePlacement(placement) === auto) {
|
|||
|
return [];
|
|||
|
}
|
|||
|
|
|||
|
var oppositePlacement = getOppositePlacement(placement);
|
|||
|
return [getOppositeVariationPlacement(placement), oppositePlacement, getOppositeVariationPlacement(oppositePlacement)];
|
|||
|
}
|
|||
|
|
|||
|
function flip(_ref) {
|
|||
|
var state = _ref.state,
|
|||
|
options = _ref.options,
|
|||
|
name = _ref.name;
|
|||
|
|
|||
|
if (state.modifiersData[name]._skip) {
|
|||
|
return;
|
|||
|
}
|
|||
|
|
|||
|
var _options$mainAxis = options.mainAxis,
|
|||
|
checkMainAxis = _options$mainAxis === void 0 ? true : _options$mainAxis,
|
|||
|
_options$altAxis = options.altAxis,
|
|||
|
checkAltAxis = _options$altAxis === void 0 ? true : _options$altAxis,
|
|||
|
specifiedFallbackPlacements = options.fallbackPlacements,
|
|||
|
padding = options.padding,
|
|||
|
boundary = options.boundary,
|
|||
|
rootBoundary = options.rootBoundary,
|
|||
|
altBoundary = options.altBoundary,
|
|||
|
_options$flipVariatio = options.flipVariations,
|
|||
|
flipVariations = _options$flipVariatio === void 0 ? true : _options$flipVariatio,
|
|||
|
allowedAutoPlacements = options.allowedAutoPlacements;
|
|||
|
var preferredPlacement = state.options.placement;
|
|||
|
var basePlacement = getBasePlacement(preferredPlacement);
|
|||
|
var isBasePlacement = basePlacement === preferredPlacement;
|
|||
|
var fallbackPlacements = specifiedFallbackPlacements || (isBasePlacement || !flipVariations ? [getOppositePlacement(preferredPlacement)] : getExpandedFallbackPlacements(preferredPlacement));
|
|||
|
var placements = [preferredPlacement].concat(fallbackPlacements).reduce(function (acc, placement) {
|
|||
|
return acc.concat(getBasePlacement(placement) === auto ? computeAutoPlacement(state, {
|
|||
|
placement: placement,
|
|||
|
boundary: boundary,
|
|||
|
rootBoundary: rootBoundary,
|
|||
|
padding: padding,
|
|||
|
flipVariations: flipVariations,
|
|||
|
allowedAutoPlacements: allowedAutoPlacements
|
|||
|
}) : placement);
|
|||
|
}, []);
|
|||
|
var referenceRect = state.rects.reference;
|
|||
|
var popperRect = state.rects.popper;
|
|||
|
var checksMap = new Map();
|
|||
|
var makeFallbackChecks = true;
|
|||
|
var firstFittingPlacement = placements[0];
|
|||
|
|
|||
|
for (var i = 0; i < placements.length; i++) {
|
|||
|
var placement = placements[i];
|
|||
|
|
|||
|
var _basePlacement = getBasePlacement(placement);
|
|||
|
|
|||
|
var isStartVariation = getVariation(placement) === start;
|
|||
|
var isVertical = [top, bottom].indexOf(_basePlacement) >= 0;
|
|||
|
var len = isVertical ? 'width' : 'height';
|
|||
|
var overflow = detectOverflow(state, {
|
|||
|
placement: placement,
|
|||
|
boundary: boundary,
|
|||
|
rootBoundary: rootBoundary,
|
|||
|
altBoundary: altBoundary,
|
|||
|
padding: padding
|
|||
|
});
|
|||
|
var mainVariationSide = isVertical ? isStartVariation ? right : left : isStartVariation ? bottom : top;
|
|||
|
|
|||
|
if (referenceRect[len] > popperRect[len]) {
|
|||
|
mainVariationSide = getOppositePlacement(mainVariationSide);
|
|||
|
}
|
|||
|
|
|||
|
var altVariationSide = getOppositePlacement(mainVariationSide);
|
|||
|
var checks = [];
|
|||
|
|
|||
|
if (checkMainAxis) {
|
|||
|
checks.push(overflow[_basePlacement] <= 0);
|
|||
|
}
|
|||
|
|
|||
|
if (checkAltAxis) {
|
|||
|
checks.push(overflow[mainVariationSide] <= 0, overflow[altVariationSide] <= 0);
|
|||
|
}
|
|||
|
|
|||
|
if (checks.every(function (check) {
|
|||
|
return check;
|
|||
|
})) {
|
|||
|
firstFittingPlacement = placement;
|
|||
|
makeFallbackChecks = false;
|
|||
|
break;
|
|||
|
}
|
|||
|
|
|||
|
checksMap.set(placement, checks);
|
|||
|
}
|
|||
|
|
|||
|
if (makeFallbackChecks) {
|
|||
|
// `2` may be desired in some cases – research later
|
|||
|
var numberOfChecks = flipVariations ? 3 : 1;
|
|||
|
|
|||
|
var _loop = function _loop(_i) {
|
|||
|
var fittingPlacement = placements.find(function (placement) {
|
|||
|
var checks = checksMap.get(placement);
|
|||
|
|
|||
|
if (checks) {
|
|||
|
return checks.slice(0, _i).every(function (check) {
|
|||
|
return check;
|
|||
|
});
|
|||
|
}
|
|||
|
});
|
|||
|
|
|||
|
if (fittingPlacement) {
|
|||
|
firstFittingPlacement = fittingPlacement;
|
|||
|
return "break";
|
|||
|
}
|
|||
|
};
|
|||
|
|
|||
|
for (var _i = numberOfChecks; _i > 0; _i--) {
|
|||
|
var _ret = _loop(_i);
|
|||
|
|
|||
|
if (_ret === "break") break;
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
if (state.placement !== firstFittingPlacement) {
|
|||
|
state.modifiersData[name]._skip = true;
|
|||
|
state.placement = firstFittingPlacement;
|
|||
|
state.reset = true;
|
|||
|
}
|
|||
|
} // eslint-disable-next-line import/no-unused-modules
|
|||
|
|
|||
|
|
|||
|
export default {
|
|||
|
name: 'flip',
|
|||
|
enabled: true,
|
|||
|
phase: 'main',
|
|||
|
fn: flip,
|
|||
|
requiresIfExists: ['offset'],
|
|||
|
data: {
|
|||
|
_skip: false
|
|||
|
}
|
|||
|
};
|