Fixed popup scroll positioning (#1507)

Signed-off-by: Andrey Sobolev <haiodo@gmail.com>
This commit is contained in:
Andrey Sobolev 2022-04-24 23:41:09 +07:00 committed by GitHub
parent d47b35dc69
commit 94ac94c1a4
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -113,44 +113,53 @@ export function closeDatePopup (): void {
*
* return boolean to show or not modal overlay.
*/
export function fitPopupPositionedElement (modalHTML: HTMLElement, alignment: PopupPositionElement): boolean {
export function fitPopupPositionedElement (modalHTML: HTMLElement, alignment: PopupPositionElement, newProps: Record<string, string|number>): boolean {
const rect = alignment.getBoundingClientRect()
const rectPopup = modalHTML.getBoundingClientRect()
modalHTML.style.left = modalHTML.style.right = modalHTML.style.top = modalHTML.style.bottom = ''
modalHTML.style.maxHeight = modalHTML.style.height = ''
modalHTML.style.maxWidth = modalHTML.style.width = ''
newProps.left = newProps.right = newProps.top = newProps.bottom = ''
newProps.maxHeight = newProps.height = ''
newProps.maxWidth = newProps.width = ''
if (alignment.position !== undefined) {
if (alignment.position.v === 'top') {
modalHTML.style.top = `${rect.top}px`
newProps.top = `${rect.top}px`
} else if (alignment.position.v === 'bottom') {
modalHTML.style.top = `${rect.bottom - rectPopup.height}px`
newProps.top = `${rect.bottom - rectPopup.height}px`
}
if (alignment.position.h === 'right') {
modalHTML.style.left = `calc(${rect.right}px + .125rem)`
newProps.left = `calc(${rect.right}px + .125rem)`
} else if (alignment.position.h === 'left') {
modalHTML.style.left = `calc(${rect.left - rectPopup.width}px - .125rem)`
newProps.left = `calc(${rect.left - rectPopup.width}px - .125rem)`
}
} else {
// Vertical
if (rect.bottom + rectPopup.height + 28 <= document.body.clientHeight) {
modalHTML.style.top = `calc(${rect.bottom}px + .125rem)`
newProps.top = `calc(${rect.bottom}px + .125rem)`
} else if (rectPopup.height + 28 < rect.top) {
modalHTML.style.bottom = `calc(${document.body.clientHeight - rect.y}px + .125rem)`
newProps.bottom = `calc(${document.body.clientHeight - rect.y}px + .125rem)`
} else {
modalHTML.style.top = modalHTML.style.bottom = '1rem'
newProps.top = modalHTML.style.bottom = '1rem'
}
// Horizontal
if (rect.left + rectPopup.width + 16 > document.body.clientWidth) {
modalHTML.style.right = `${document.body.clientWidth - rect.right}px`
newProps.right = `${document.body.clientWidth - rect.right}px`
} else {
modalHTML.style.left = `${rect.left}px`
newProps.left = `${rect.left}px`
}
}
return false
}
function applyStyle (values: Record<string, string| number>, modalHTML: HTMLElement): void {
for (const [k, v] of Object.entries(values)) {
const old = (modalHTML.style as any)[k]
if (old !== v) {
(modalHTML.style as any)[k] = v
}
}
}
/**
* @public
*
@ -160,57 +169,61 @@ export function fitPopupPositionedElement (modalHTML: HTMLElement, alignment: Po
*/
export function fitPopupElement (modalHTML: HTMLElement, element?: PopupAlignment, contentPanel?: HTMLElement): boolean {
let show = true
const newProps: Record<string, string|number> = {}
if (element != null) {
show = false
modalHTML.style.left = modalHTML.style.right = modalHTML.style.top = modalHTML.style.bottom = ''
modalHTML.style.maxHeight = modalHTML.style.height = ''
newProps.left = newProps.right = newProps.top = newProps.bottom = ''
newProps.maxHeight = newProps.height = ''
if (typeof element !== 'string') {
return fitPopupPositionedElement(modalHTML, element)
const result = fitPopupPositionedElement(modalHTML, element, newProps)
applyStyle(newProps, modalHTML)
return result
} else if (element === 'right' && contentPanel !== undefined) {
const rect = contentPanel.getBoundingClientRect()
modalHTML.style.top = `calc(${rect.top}px + 0.5rem)`
modalHTML.style.bottom = '0.75rem'
modalHTML.style.right = '0.75rem'
modalHTML.style.maxWidth = '50%'
newProps.top = `calc(${rect.top}px + 0.5rem)`
newProps.bottom = '0.75rem'
newProps.right = '0.75rem'
newProps.maxWidth = '50%'
show = true
} else if (element === 'top') {
modalHTML.style.top = '15vh'
modalHTML.style.left = '50%'
modalHTML.style.transform = 'translateX(-50%)'
newProps.top = '15vh'
newProps.left = '50%'
newProps.transform = 'translateX(-50%)'
show = true
} else if (element === 'account') {
modalHTML.style.bottom = '2.75rem'
modalHTML.style.left = '5rem'
newProps.bottom = '2.75rem'
newProps.left = '5rem'
} else if (element === 'full' && contentPanel !== undefined) {
const rect = contentPanel.getBoundingClientRect()
modalHTML.style.top = `calc(${rect.top}px + 0.25rem)`
modalHTML.style.bottom = '0.25rem'
modalHTML.style.left = '0.25rem'
modalHTML.style.right = '0.25rem'
newProps.top = `calc(${rect.top}px + 0.25rem)`
newProps.bottom = '0.25rem'
newProps.left = '0.25rem'
newProps.right = '0.25rem'
show = true
} else if (element === 'content' && contentPanel !== undefined) {
const rect = contentPanel.getBoundingClientRect()
modalHTML.style.top = `${rect.top + 1}px`
modalHTML.style.height = `${Math.min(rect.height - 1, window.innerHeight - rect.top - 1)}px`
modalHTML.style.left = `${rect.left + 1}px`
modalHTML.style.width = `${Math.min(rect.width - 1, window.innerWidth - rect.left - 1)}px`
newProps.top = `${rect.top + 1}px`
newProps.height = `${Math.min(rect.height - 1, window.innerHeight - rect.top - 1)}px`
newProps.left = `${rect.left + 1}px`
newProps.width = `${Math.min(rect.width - 1, window.innerWidth - rect.left - 1)}px`
} else if (element === 'middle') {
if (contentPanel !== undefined) {
const rect = contentPanel.getBoundingClientRect()
modalHTML.style.top = `calc(${rect.top}px)`
newProps.top = `calc(${rect.top}px)`
} else {
modalHTML.style.top = '15%'
newProps.top = '15%'
}
modalHTML.style.bottom = '0.75rem'
modalHTML.style.left = '50%'
modalHTML.style.transform = 'translateX(-50%)'
newProps.bottom = '0.75rem'
newProps.left = '50%'
newProps.transform = 'translateX(-50%)'
}
} else {
modalHTML.style.top = '50%'
modalHTML.style.left = '50%'
modalHTML.style.transform = 'translate(-50%, -50%)'
newProps.top = '50%'
newProps.left = '50%'
newProps.transform = 'translate(-50%, -50%)'
show = true
}
applyStyle(newProps, modalHTML)
return show
}