forked from floating-ui/floating-ui
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
fix(DOM): iOS safari pinch zooming fix
This is an amendment from @floating-ui adapted to @popperjs and flow fix floating-ui#1121 re floating-ui#1576
- Loading branch information
Mateusz Daniluk
committed
Aug 6, 2022
1 parent
593aefe
commit aa63fe1
Showing
6 changed files
with
88 additions
and
50 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,38 +1,49 @@ | ||
// @flow | ||
import type { ClientRectObject, VirtualElement } from '../types'; | ||
import { isHTMLElement } from './instanceOf'; | ||
import { isElement, isHTMLElement} from './instanceOf'; | ||
import { round } from '../utils/math'; | ||
import getWindow from './getWindow'; | ||
import isLayoutViewport from './isLayoutViewport'; | ||
|
||
export default function getBoundingClientRect( | ||
element: Element | VirtualElement, | ||
includeScale: boolean = false | ||
includeScale: boolean = false, | ||
isFixedStrategy: boolean = false | ||
): ClientRectObject { | ||
const rect = element.getBoundingClientRect(); | ||
const clientRect = element.getBoundingClientRect(); | ||
let scaleX = 1; | ||
let scaleY = 1; | ||
|
||
if (isHTMLElement(element) && includeScale) { | ||
const offsetHeight = element.offsetHeight; | ||
const offsetWidth = element.offsetWidth; | ||
|
||
// Do not attempt to divide by 0, otherwise we get `Infinity` as scale | ||
// Fallback to 1 in case both values are `0` | ||
if (offsetWidth > 0) { | ||
scaleX = round(rect.width) / offsetWidth || 1; | ||
} | ||
if (offsetHeight > 0) { | ||
scaleY = round(rect.height) / offsetHeight || 1; | ||
} | ||
if (includeScale && isHTMLElement(element)) { | ||
scaleX = | ||
(element: HTMLElement).offsetWidth > 0 | ||
? round(clientRect.width) / (element: HTMLElement).offsetWidth || 1 | ||
: 1; | ||
scaleY = | ||
(element: HTMLElement).offsetHeight > 0 | ||
? round(clientRect.height) / (element: HTMLElement).offsetHeight || 1 | ||
: 1; | ||
} | ||
|
||
const {visualViewport} = isElement(element) ? getWindow(element) : window; | ||
const addVisualOffsets = !isLayoutViewport() && isFixedStrategy; | ||
|
||
const x = | ||
(clientRect.left + (addVisualOffsets && visualViewport ? visualViewport.offsetLeft : 0)) / | ||
scaleX; | ||
const y = | ||
(clientRect.top + (addVisualOffsets && visualViewport ? visualViewport.offsetTop : 0)) / | ||
scaleY; | ||
const width = clientRect.width / scaleX; | ||
const height = clientRect.height / scaleY; | ||
return { | ||
width: rect.width / scaleX, | ||
height: rect.height / scaleY, | ||
top: rect.top / scaleY, | ||
right: rect.right / scaleX, | ||
bottom: rect.bottom / scaleY, | ||
left: rect.left / scaleX, | ||
x: rect.left / scaleX, | ||
y: rect.top / scaleY, | ||
width, | ||
height, | ||
top: y, | ||
right: x + width, | ||
bottom: y + height, | ||
left: x, | ||
x, | ||
y | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
// @flow | ||
type Navigator = Navigator & { userAgentData?: NavigatorUAData }; | ||
|
||
interface NavigatorUAData { | ||
brands: Array<{brand: string; version: string}>; | ||
mobile: boolean; | ||
platform: string; | ||
} | ||
|
||
function getUAString(): string { | ||
|
||
const uaData = (navigator: Navigator).userAgentData; | ||
|
||
if (uaData?.brands) { | ||
return uaData.brands | ||
.map((item) => `${item.brand}/${item.version}`) | ||
.join(' '); | ||
} | ||
|
||
return navigator.userAgent; | ||
} | ||
|
||
export default function isLayoutViewport() { | ||
return !/^((?!chrome|android).)*safari/i.test(getUAString()); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters