mirror of
https://github.com/ionic-team/ionic-framework.git
synced 2025-08-19 03:32:21 +08:00
fix(nav): prevent completing transition from being interrupted (#19113)
* do not enable swipe to begin before previous one has ended * update defaults * use canStart instead * pause animations on finish * remove old pause code
This commit is contained in:
@ -18,6 +18,7 @@ export class Nav implements NavOutlet {
|
|||||||
|
|
||||||
private transInstr: TransitionInstruction[] = [];
|
private transInstr: TransitionInstruction[] = [];
|
||||||
private sbAni?: Animation | IonicAnimation;
|
private sbAni?: Animation | IonicAnimation;
|
||||||
|
private animationEnabled = true;
|
||||||
private useRouter = false;
|
private useRouter = false;
|
||||||
private isTransitioning = false;
|
private isTransitioning = false;
|
||||||
private destroyed = false;
|
private destroyed = false;
|
||||||
@ -937,6 +938,7 @@ export class Nav implements NavOutlet {
|
|||||||
!!this.swipeGesture &&
|
!!this.swipeGesture &&
|
||||||
!this.isTransitioning &&
|
!this.isTransitioning &&
|
||||||
this.transInstr.length === 0 &&
|
this.transInstr.length === 0 &&
|
||||||
|
this.animationEnabled &&
|
||||||
this.canGoBackSync()
|
this.canGoBackSync()
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -960,6 +962,10 @@ export class Nav implements NavOutlet {
|
|||||||
|
|
||||||
private onEnd(shouldComplete: boolean, stepValue: number, dur: number) {
|
private onEnd(shouldComplete: boolean, stepValue: number, dur: number) {
|
||||||
if (this.sbAni) {
|
if (this.sbAni) {
|
||||||
|
this.animationEnabled = false;
|
||||||
|
this.sbAni.onFinish(() => {
|
||||||
|
this.animationEnabled = true;
|
||||||
|
}, { oneTimeCallback: true });
|
||||||
this.sbAni.progressEnd(shouldComplete, stepValue, dur);
|
this.sbAni.progressEnd(shouldComplete, stepValue, dur);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -18,6 +18,7 @@ export class RouterOutlet implements ComponentInterface, NavOutlet {
|
|||||||
private waitPromise?: Promise<void>;
|
private waitPromise?: Promise<void>;
|
||||||
private gesture?: Gesture;
|
private gesture?: Gesture;
|
||||||
private ani?: IonicAnimation | Animation;
|
private ani?: IonicAnimation | Animation;
|
||||||
|
private animationEnabled = true;
|
||||||
|
|
||||||
@Element() el!: HTMLElement;
|
@Element() el!: HTMLElement;
|
||||||
|
|
||||||
@ -65,12 +66,18 @@ export class RouterOutlet implements ComponentInterface, NavOutlet {
|
|||||||
async componentDidLoad() {
|
async componentDidLoad() {
|
||||||
this.gesture = (await import('../../utils/gesture/swipe-back')).createSwipeBackGesture(
|
this.gesture = (await import('../../utils/gesture/swipe-back')).createSwipeBackGesture(
|
||||||
this.el,
|
this.el,
|
||||||
() => !!this.swipeHandler && this.swipeHandler.canStart(),
|
() => !!this.swipeHandler && this.swipeHandler.canStart() && this.animationEnabled,
|
||||||
() => this.swipeHandler && this.swipeHandler.onStart(),
|
() => this.swipeHandler && this.swipeHandler.onStart(),
|
||||||
step => this.ani && this.ani.progressStep(step),
|
step => this.ani && this.ani.progressStep(step),
|
||||||
(shouldComplete, step, dur) => {
|
(shouldComplete, step, dur) => {
|
||||||
if (this.ani) {
|
if (this.ani) {
|
||||||
|
this.animationEnabled = false;
|
||||||
|
this.ani.onFinish(() => {
|
||||||
|
this.animationEnabled = true;
|
||||||
|
}, { oneTimeCallback: true });
|
||||||
|
|
||||||
this.ani.progressEnd(shouldComplete, step, dur);
|
this.ani.progressEnd(shouldComplete, step, dur);
|
||||||
|
|
||||||
}
|
}
|
||||||
if (this.swipeHandler) {
|
if (this.swipeHandler) {
|
||||||
this.swipeHandler.onEnd(shouldComplete);
|
this.swipeHandler.onEnd(shouldComplete);
|
||||||
|
@ -604,7 +604,7 @@ export const createAnimation = () => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const initializeCSSAnimation = () => {
|
const initializeCSSAnimation = (toggleAnimationName = true) => {
|
||||||
cleanUpStyleSheets();
|
cleanUpStyleSheets();
|
||||||
|
|
||||||
elements.forEach(element => {
|
elements.forEach(element => {
|
||||||
@ -628,7 +628,10 @@ export const createAnimation = () => {
|
|||||||
setStyleProperty(element, 'animation-iteration-count', iterationsCount);
|
setStyleProperty(element, 'animation-iteration-count', iterationsCount);
|
||||||
setStyleProperty(element, 'animation-play-state', 'paused');
|
setStyleProperty(element, 'animation-play-state', 'paused');
|
||||||
|
|
||||||
setStyleProperty(element, 'animation-name', `${stylesheet.id}-alt`);
|
if (toggleAnimationName) {
|
||||||
|
setStyleProperty(element, 'animation-name', `${stylesheet.id}-alt`);
|
||||||
|
}
|
||||||
|
|
||||||
requestAnimationFrame(() => {
|
requestAnimationFrame(() => {
|
||||||
setStyleProperty(element, 'animation-name', stylesheet.id || null);
|
setStyleProperty(element, 'animation-name', stylesheet.id || null);
|
||||||
});
|
});
|
||||||
@ -660,14 +663,14 @@ export const createAnimation = () => {
|
|||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const initializeAnimation = () => {
|
const initializeAnimation = (toggleAnimationName = true) => {
|
||||||
beforeAnimation();
|
beforeAnimation();
|
||||||
|
|
||||||
if (_keyframes.length > 0) {
|
if (_keyframes.length > 0) {
|
||||||
if (supportsWebAnimations) {
|
if (supportsWebAnimations) {
|
||||||
initializeWebAnimation();
|
initializeWebAnimation();
|
||||||
} else {
|
} else {
|
||||||
initializeCSSAnimation();
|
initializeCSSAnimation(toggleAnimationName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -968,7 +971,7 @@ export const createAnimation = () => {
|
|||||||
*/
|
*/
|
||||||
const play = () => {
|
const play = () => {
|
||||||
if (!initialized) {
|
if (!initialized) {
|
||||||
initializeAnimation();
|
initializeAnimation(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (finished) {
|
if (finished) {
|
||||||
|
Reference in New Issue
Block a user