在Angular 2中的路线之间导航时显示加载屏幕

Angular 2中更改路线时如何显示加载屏幕?

回答:

当前的AngularRouter提供导航事件。您可以订阅这些内容并相应地更改UI。请记住要计入其他事件,例如,NavigationCancelNavigationError在路由器转换失败时停止旋转器。

app.component.ts- 您的根组件

...

import {

Router,

// import as RouterEvent to avoid confusion with the DOM Event

Event as RouterEvent,

NavigationStart,

NavigationEnd,

NavigationCancel,

NavigationError

} from '@angular/router'

@Component({})

export class AppComponent {

// Sets initial value to true to show loading spinner on first load

loading = true

constructor(private router: Router) {

this.router.events.subscribe((e : RouterEvent) => {

this.navigationInterceptor(e);

})

}

// Shows and hides the loading spinner during RouterEvent changes

navigationInterceptor(event: RouterEvent): void {

if (event instanceof NavigationStart) {

this.loading = true

}

if (event instanceof NavigationEnd) {

this.loading = false

}

// Set loading state to false in both of the below events to hide the spinner in case a request fails

if (event instanceof NavigationCancel) {

this.loading = false

}

if (event instanceof NavigationError) {

this.loading = false

}

}

}

app.component.html- 您的根视图

<div class="loading-overlay" *ngIf="loading">

<!-- show something fancy here, here with Angular 2 Material's loading bar or circle -->

<md-progress-bar mode="indeterminate"></md-progress-bar>

</div>

:如果您关心性能,有更好的方法,则实现起来会有些繁琐,但是提高性能值得进行额外的工作。代替使用*ngIf有条件地显示微调器,我们可以利用Angular的功能NgZoneRenderer打开/关闭微调器,这将在我们更改微调器的状态时绕过Angular的更改检测。与使用*ngIfasync管道相比,我发现这可以使动画更流畅。

这与我以前的回答类似,但有一些调整:

app.component.ts- 您的根组件

...

import {

Router,

// import as RouterEvent to avoid confusion with the DOM Event

Event as RouterEvent,

NavigationStart,

NavigationEnd,

NavigationCancel,

NavigationError

} from '@angular/router'

import {NgZone, Renderer, ElementRef, ViewChild} from '@angular/core'

@Component({})

export class AppComponent {

// Instead of holding a boolean value for whether the spinner

// should show or not, we store a reference to the spinner element,

// see template snippet below this script

@ViewChild('spinnerElement')

spinnerElement: ElementRef

constructor(private router: Router,

private ngZone: NgZone,

private renderer: Renderer) {

router.events.subscribe(this._navigationInterceptor)

}

// Shows and hides the loading spinner during RouterEvent changes

private _navigationInterceptor(event: RouterEvent): void {

if (event instanceof NavigationStart) {

// We wanna run this function outside of Angular's zone to

// bypass change detection

this.ngZone.runOutsideAngular(() => {

// For simplicity we are going to turn opacity on / off

// you could add/remove a class for more advanced styling

// and enter/leave animation of the spinner

this.renderer.setElementStyle(

this.spinnerElement.nativeElement,

'opacity',

'1'

)

})

}

if (event instanceof NavigationEnd) {

this._hideSpinner()

}

// Set loading state to false in both of the below events to

// hide the spinner in case a request fails

if (event instanceof NavigationCancel) {

this._hideSpinner()

}

if (event instanceof NavigationError) {

this._hideSpinner()

}

}

private _hideSpinner(): void {

// We wanna run this function outside of Angular's zone to

// bypass change detection,

this.ngZone.runOutsideAngular(() => {

// For simplicity we are going to turn opacity on / off

// you could add/remove a class for more advanced styling

// and enter/leave animation of the spinner

this.renderer.setElementStyle(

this.spinnerElement.nativeElement,

'opacity',

'0'

)

})

}

}

app.component.html- 您的根视图

<div class="loading-overlay" #spinnerElement style="opacity: 0;">

<!-- md-spinner is short for <md-progress-circle mode="indeterminate"></md-progress-circle> -->

<md-spinner></md-spinner>

</div>

以上是 在Angular 2中的路线之间导航时显示加载屏幕 的全部内容, 来源链接: utcz.com/qa/399689.html

回到顶部