source: imaps-frontend/node_modules/@popperjs/core/lib/utils/detectOverflow.js.flow

main
Last change on this file was d565449, checked in by stefan toskovski <stefantoska84@…>, 4 weeks ago

Update repo after prototype presentation

  • Property mode set to 100644
File size: 3.2 KB
Line 
1// @flow
2import type { State, SideObject, Padding, PositioningStrategy } from '../types';
3import type { Placement, Boundary, RootBoundary, Context } from '../enums';
4import getClippingRect from '../dom-utils/getClippingRect';
5import getDocumentElement from '../dom-utils/getDocumentElement';
6import getBoundingClientRect from '../dom-utils/getBoundingClientRect';
7import computeOffsets from './computeOffsets';
8import rectToClientRect from './rectToClientRect';
9import {
10 clippingParents,
11 reference,
12 popper,
13 bottom,
14 top,
15 right,
16 basePlacements,
17 viewport,
18} from '../enums';
19import { isElement } from '../dom-utils/instanceOf';
20import mergePaddingObject from './mergePaddingObject';
21import expandToHashMap from './expandToHashMap';
22
23// eslint-disable-next-line import/no-unused-modules
24export type Options = {
25 placement: Placement,
26 strategy: PositioningStrategy,
27 boundary: Boundary,
28 rootBoundary: RootBoundary,
29 elementContext: Context,
30 altBoundary: boolean,
31 padding: Padding,
32};
33
34export default function detectOverflow(
35 state: State,
36 options: $Shape<Options> = {}
37): SideObject {
38 const {
39 placement = state.placement,
40 strategy = state.strategy,
41 boundary = clippingParents,
42 rootBoundary = viewport,
43 elementContext = popper,
44 altBoundary = false,
45 padding = 0,
46 } = options;
47
48 const paddingObject = mergePaddingObject(
49 typeof padding !== 'number'
50 ? padding
51 : expandToHashMap(padding, basePlacements)
52 );
53
54 const altContext = elementContext === popper ? reference : popper;
55
56 const popperRect = state.rects.popper;
57 const element = state.elements[altBoundary ? altContext : elementContext];
58
59 const clippingClientRect = getClippingRect(
60 isElement(element)
61 ? element
62 : element.contextElement || getDocumentElement(state.elements.popper),
63 boundary,
64 rootBoundary,
65 strategy
66 );
67
68 const referenceClientRect = getBoundingClientRect(state.elements.reference);
69
70 const popperOffsets = computeOffsets({
71 reference: referenceClientRect,
72 element: popperRect,
73 strategy: 'absolute',
74 placement,
75 });
76
77 const popperClientRect = rectToClientRect({
78 ...popperRect,
79 ...popperOffsets,
80 });
81
82 const elementClientRect =
83 elementContext === popper ? popperClientRect : referenceClientRect;
84
85 // positive = overflowing the clipping rect
86 // 0 or negative = within the clipping rect
87 const overflowOffsets = {
88 top: clippingClientRect.top - elementClientRect.top + paddingObject.top,
89 bottom:
90 elementClientRect.bottom -
91 clippingClientRect.bottom +
92 paddingObject.bottom,
93 left: clippingClientRect.left - elementClientRect.left + paddingObject.left,
94 right:
95 elementClientRect.right - clippingClientRect.right + paddingObject.right,
96 };
97
98 const offsetData = state.modifiersData.offset;
99
100 // Offsets can be applied only to the popper element
101 if (elementContext === popper && offsetData) {
102 const offset = offsetData[placement];
103
104 Object.keys(overflowOffsets).forEach((key) => {
105 const multiply = [right, bottom].indexOf(key) >= 0 ? 1 : -1;
106 const axis = [top, bottom].indexOf(key) >= 0 ? 'y' : 'x';
107 overflowOffsets[key] += offset[axis] * multiply;
108 });
109 }
110
111 return overflowOffsets;
112}
Note: See TracBrowser for help on using the repository browser.