feat(angular): expose animationDirection (#16802)

* feat(angular): expose animationDirection

* update
This commit is contained in:
Manu MA
2018-12-18 20:17:16 +01:00
committed by GitHub
parent dfbb5b6e6e
commit 320eb03168
4 changed files with 57 additions and 42 deletions

View File

@ -64,6 +64,6 @@ export class IonTabs {
? href ? href
: this.outlet.getLastUrl(tab) || href; : this.outlet.getLastUrl(tab) || href;
return this.navCtrl.navigateBack(url, true); return this.navCtrl.navigateBack(url);
} }
} }

View File

@ -1,9 +1,10 @@
import { LocationStrategy } from '@angular/common'; import { LocationStrategy } from '@angular/common';
import { Directive, ElementRef, HostListener, Input, Optional } from '@angular/core'; import { Directive, ElementRef, HostListener, Input, Optional } from '@angular/core';
import { Router, RouterLink } from '@angular/router'; import { Router, RouterLink } from '@angular/router';
import { RouterDirection } from '@ionic/core';
import { Subscription } from 'rxjs'; import { Subscription } from 'rxjs';
import { NavController, NavDirection } from '../../providers/nav-controller'; import { NavController } from '../../providers/nav-controller';
@Directive({ @Directive({
selector: '[routerLink]', selector: '[routerLink]',
@ -12,7 +13,7 @@ export class RouterLinkDelegate {
private subscription?: Subscription; private subscription?: Subscription;
@Input() routerDirection: NavDirection = 'forward'; @Input() routerDirection: RouterDirection = 'forward';
constructor( constructor(
private locationStrategy: LocationStrategy, private locationStrategy: LocationStrategy,

View File

@ -2,7 +2,7 @@ import { ComponentRef, NgZone } from '@angular/core';
import { ActivatedRoute, Router } from '@angular/router'; import { ActivatedRoute, Router } from '@angular/router';
import { RouterDirection } from '@ionic/core'; import { RouterDirection } from '@ionic/core';
import { NavController, NavDirection } from '../../providers/nav-controller'; import { NavController } from '../../providers/nav-controller';
import { RouteView, computeStackId, destroyView, getUrl, insertView, isTabSwitch, toSegments } from './stack-utils'; import { RouteView, computeStackId, destroyView, getUrl, insertView, isTabSwitch, toSegments } from './stack-utils';
@ -43,14 +43,14 @@ export class StackController {
} }
async setActive(enteringView: RouteView) { async setActive(enteringView: RouteView) {
let { direction, animated } = this.navCtrl.consumeTransition(); let { direction, animation } = this.navCtrl.consumeTransition();
const leavingView = this.activeView; const leavingView = this.activeView;
if (isTabSwitch(enteringView, leavingView)) { if (isTabSwitch(enteringView, leavingView)) {
direction = 'back'; direction = 'back';
animated = false; animation = undefined;
} }
this.insertView(enteringView, direction); this.insertView(enteringView, direction);
await this.transition(enteringView, leavingView, direction, animated, this.canGoBack(1), false); await this.transition(enteringView, leavingView, animation, this.canGoBack(1), false);
this.cleanup(); this.cleanup();
} }
@ -73,7 +73,6 @@ export class StackController {
views[views.length - 1], // leaving view views[views.length - 1], // leaving view
'back', 'back',
true, true,
true,
true true
); );
} }
@ -130,8 +129,7 @@ export class StackController {
private async transition( private async transition(
enteringView: RouteView | undefined, enteringView: RouteView | undefined,
leavingView: RouteView | undefined, leavingView: RouteView | undefined,
direction: NavDirection, direction: 'forward' | 'back' | undefined,
animated: boolean,
showGoBack: boolean, showGoBack: boolean,
progressAnimation: boolean progressAnimation: boolean
) { ) {
@ -159,9 +157,9 @@ export class StackController {
await containerEl.componentOnReady(); await containerEl.componentOnReady();
this.runningTransition = containerEl.commit(enteringEl, leavingEl, { this.runningTransition = containerEl.commit(enteringEl, leavingEl, {
duration: !animated ? 0 : undefined,
direction: direction === 'forward' ? 'forward' : 'back', // TODO: refactor
deepWait: true, deepWait: true,
duration: direction === undefined ? 0 : undefined,
direction,
showGoBack, showGoBack,
progressAnimation progressAnimation
}); });

View File

@ -1,19 +1,24 @@
import { Location } from '@angular/common'; import { Location } from '@angular/common';
import { Injectable, Optional } from '@angular/core'; import { Injectable, Optional } from '@angular/core';
import { NavigationExtras, NavigationStart, Router, UrlTree } from '@angular/router'; import { NavigationExtras, NavigationStart, Router, UrlTree } from '@angular/router';
import { RouterDirection } from '@ionic/core'; import { NavDirection, RouterDirection } from '@ionic/core';
import { Platform } from './platform'; import { Platform } from './platform';
export type NavDirection = 'forward' | 'back' | 'root' | 'auto'; export interface AnimationOptions {
animated?: boolean;
animationDirection?: 'forward' | 'back';
}
export interface NavigationOptions extends NavigationExtras, AnimationOptions {}
@Injectable() @Injectable()
export class NavController { export class NavController {
private direction: NavDirection = DEFAULT_DIRECTION; private direction: 'forward' | 'back' | 'root' | 'auto' = DEFAULT_DIRECTION;
private animated = DEFAULT_ANIMATED; private animated?: NavDirection = DEFAULT_ANIMATED;
private guessDirection: RouterDirection = 'forward'; private guessDirection: RouterDirection = 'forward';
private guessAnimation = false; private guessAnimation?: NavDirection;
private lastNavId = -1; private lastNavId = -1;
constructor( constructor(
@ -26,8 +31,8 @@ export class NavController {
router.events.subscribe(ev => { router.events.subscribe(ev => {
if (ev instanceof NavigationStart) { if (ev instanceof NavigationStart) {
const id = (ev.restoredState) ? ev.restoredState.navigationId : ev.id; const id = (ev.restoredState) ? ev.restoredState.navigationId : ev.id;
this.guessAnimation = !ev.restoredState;
this.guessDirection = id < this.lastNavId ? 'back' : 'forward'; this.guessDirection = id < this.lastNavId ? 'back' : 'forward';
this.guessAnimation = !ev.restoredState ? this.guessDirection : undefined;
this.lastNavId = this.guessDirection === 'forward' ? ev.id : id; this.lastNavId = this.guessDirection === 'forward' ? ev.id : id;
} }
}); });
@ -37,55 +42,53 @@ export class NavController {
platform.backButton.subscribeWithPriority(0, () => this.goBack()); platform.backButton.subscribeWithPriority(0, () => this.goBack());
} }
navigateForward(url: string | UrlTree | any[], animated?: boolean, extras?: NavigationExtras) { navigateForward(url: string | UrlTree | any[], options: NavigationOptions = {}) {
this.setDirection('forward', animated); this.setDirection('forward', options.animated, options.animationDirection);
if (Array.isArray(url)) { if (Array.isArray(url)) {
return this.router!.navigate(url, extras); return this.router!.navigate(url, options);
} else { } else {
return this.router!.navigateByUrl(url, extras); return this.router!.navigateByUrl(url, options);
} }
} }
navigateBack(url: string | UrlTree | any[], animated?: boolean, extras?: NavigationExtras) { navigateBack(url: string | UrlTree | any[], options: NavigationOptions = {}) {
this.setDirection('back', animated); this.setDirection('back', options.animated, options.animationDirection);
// extras = { replaceUrl: true, ...extras }; // extras = { replaceUrl: true, ...extras };
if (Array.isArray(url)) { if (Array.isArray(url)) {
return this.router!.navigate(url, extras); return this.router!.navigate(url, options);
} else { } else {
return this.router!.navigateByUrl(url, extras); return this.router!.navigateByUrl(url, options);
} }
} }
navigateRoot(url: string | UrlTree | any[], animated?: boolean, extras?: NavigationExtras) { navigateRoot(url: string | UrlTree | any[], options: NavigationOptions = {}) {
this.setDirection('root', animated); this.setDirection('root', options.animated, options.animationDirection);
if (Array.isArray(url)) { if (Array.isArray(url)) {
return this.router!.navigate(url, extras); return this.router!.navigate(url, options);
} else { } else {
return this.router!.navigateByUrl(url, extras); return this.router!.navigateByUrl(url, options);
} }
} }
goBack(animated?: boolean) { goBack(options: AnimationOptions = { animated: true, animationDirection: 'back' }) {
this.setDirection('back', animated); this.setDirection('back', options.animated, options.animationDirection);
return this.location.back(); return this.location.back();
} }
setDirection(direction: NavDirection, animated?: boolean) { setDirection(direction: RouterDirection, animated?: boolean, animationDirection?: 'forward' | 'back') {
this.direction = direction; this.direction = direction;
this.animated = (animated === undefined) this.animated = getAnimation(direction, animated, animationDirection);
? direction !== 'root'
: animated;
} }
consumeTransition() { consumeTransition() {
let direction: RouterDirection = 'root'; let direction: RouterDirection = 'root';
let animated = false; let animation: NavDirection | undefined;
if (this.direction === 'auto') { if (this.direction === 'auto') {
direction = this.guessDirection; direction = this.guessDirection;
animated = this.guessAnimation; animation = this.guessAnimation;
} else { } else {
animated = this.animated; animation = this.animated;
direction = this.direction; direction = this.direction;
} }
this.direction = DEFAULT_DIRECTION; this.direction = DEFAULT_DIRECTION;
@ -93,10 +96,23 @@ export class NavController {
return { return {
direction, direction,
animated animation
}; };
} }
} }
function getAnimation(direction: RouterDirection, animated: boolean | undefined, animationDirection: 'forward' | 'back' | undefined): NavDirection | undefined {
if (animated === false) {
return undefined;
}
if (animationDirection !== undefined) {
return animationDirection;
}
if (direction === 'forward' || direction === 'back') {
return direction;
}
return undefined;
}
const DEFAULT_DIRECTION = 'auto'; const DEFAULT_DIRECTION = 'auto';
const DEFAULT_ANIMATED = false; const DEFAULT_ANIMATED = undefined;