chore(mobile): optimize swipe dialog animation timeline (#9028)
This commit is contained in:
@@ -29,21 +29,21 @@ const tick = (
|
|||||||
overlay: HTMLDivElement,
|
overlay: HTMLDivElement,
|
||||||
dialog: HTMLDivElement,
|
dialog: HTMLDivElement,
|
||||||
prev: HTMLElement | null,
|
prev: HTMLElement | null,
|
||||||
deltaX: number
|
deltaX: number,
|
||||||
|
fullWidth: number
|
||||||
) => {
|
) => {
|
||||||
const limitedDeltaX = Math.min(overlay.clientWidth, Math.max(0, deltaX));
|
const limitedDeltaX = Math.min(fullWidth, Math.max(0, deltaX));
|
||||||
const percent = limitedDeltaX / overlay.clientWidth;
|
const percent = limitedDeltaX / fullWidth;
|
||||||
const opacity =
|
const opacity =
|
||||||
overlayOpacityRange[1] -
|
overlayOpacityRange[1] -
|
||||||
(overlayOpacityRange[1] - overlayOpacityRange[0]) * percent;
|
(overlayOpacityRange[1] - overlayOpacityRange[0]) * percent;
|
||||||
overlay.style.background = `rgba(0, 0, 0, ${opacity})`;
|
overlay.style.background = `rgba(0, 0, 0, ${opacity})`;
|
||||||
dialog.style.transform = `translateX(${limitedDeltaX}px)`;
|
dialog.style.transform = `translate3d(${limitedDeltaX}px, 0, 0)`;
|
||||||
|
|
||||||
const prevEl = prev ?? document.querySelector('#app');
|
if (prev) {
|
||||||
if (prevEl) {
|
|
||||||
const range = [-80, 0];
|
const range = [-80, 0];
|
||||||
const offset = range[0] + (range[1] - range[0]) * percent;
|
const offset = range[0] + (range[1] - range[0]) * percent;
|
||||||
prevEl.style.transform = `translateX(${offset}px)`;
|
prev.style.transform = `translate3d(${offset}px, 0, 0)`;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
const reset = (
|
const reset = (
|
||||||
@@ -62,16 +62,17 @@ const reset = (
|
|||||||
const getAnimeProxy = (
|
const getAnimeProxy = (
|
||||||
overlay: HTMLDivElement,
|
overlay: HTMLDivElement,
|
||||||
dialog: HTMLDivElement,
|
dialog: HTMLDivElement,
|
||||||
prev: HTMLElement | null,
|
maybePrev: HTMLElement | null,
|
||||||
init: number
|
init: number
|
||||||
) => {
|
) => {
|
||||||
|
const prev = maybePrev ?? document.querySelector('#app');
|
||||||
return new Proxy(
|
return new Proxy(
|
||||||
{ deltaX: init },
|
{ deltaX: init },
|
||||||
{
|
{
|
||||||
set(target, key, value) {
|
set(target, key, value) {
|
||||||
if (key === 'deltaX') {
|
if (key === 'deltaX') {
|
||||||
target.deltaX = value;
|
target.deltaX = value;
|
||||||
tick(overlay, dialog, prev, value);
|
tick(overlay, dialog, prev, value, overlay.clientWidth);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
@@ -95,8 +96,8 @@ const cancel = (
|
|||||||
Math.min(overlay.clientWidth, Math.max(0, deltaX))
|
Math.min(overlay.clientWidth, Math.max(0, deltaX))
|
||||||
),
|
),
|
||||||
deltaX: 0,
|
deltaX: 0,
|
||||||
easing: 'easeInOutSine',
|
easing: 'cubicBezier(.25,.36,.24,.97)',
|
||||||
duration: 230,
|
duration: 320,
|
||||||
complete: () => {
|
complete: () => {
|
||||||
complete?.();
|
complete?.();
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
@@ -121,8 +122,8 @@ const close = (
|
|||||||
Math.min(overlay.clientWidth, Math.max(0, deltaX))
|
Math.min(overlay.clientWidth, Math.max(0, deltaX))
|
||||||
),
|
),
|
||||||
deltaX: overlay.clientWidth,
|
deltaX: overlay.clientWidth,
|
||||||
easing: 'easeInOutSine',
|
easing: 'cubicBezier(.25,.36,.24,.97)',
|
||||||
duration: 230,
|
duration: 320,
|
||||||
complete: () => {
|
complete: () => {
|
||||||
complete?.();
|
complete?.();
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
@@ -178,7 +179,8 @@ export const SwipeDialog = ({
|
|||||||
preventScroll: true,
|
preventScroll: true,
|
||||||
onSwipeStart: () => {},
|
onSwipeStart: () => {},
|
||||||
onSwipe({ deltaX }) {
|
onSwipe({ deltaX }) {
|
||||||
tick(overlay, dialog, prev, deltaX);
|
const prevOrAppRoot = prev ?? document.querySelector('#app');
|
||||||
|
tick(overlay, dialog, prevOrAppRoot, deltaX, overlay.clientWidth);
|
||||||
},
|
},
|
||||||
onSwipeEnd: ({ deltaX }) => {
|
onSwipeEnd: ({ deltaX }) => {
|
||||||
const shouldClose = deltaX > overlay.clientWidth * 0.2;
|
const shouldClose = deltaX > overlay.clientWidth * 0.2;
|
||||||
|
|||||||
Reference in New Issue
Block a user