角度通用闪烁

时间:2018-04-24 09:38:32

标签: angular angular-universal

网站加载时我有一个闪烁。 下载来自服务器的HTML,然后在UI中呈现视图,并且在转换之间存在小的闪烁。

我设法通过添加:

来修复它
RouterModule.forRoot([ // ROUTES HERE ], { initialNavigation: 'enabled' })

但我想知道它为什么会发生?由于组件的延迟加载? 因此,在构建DOM的UI(角度组件)的过渡期间,我们得到了一个闪烁?让我们说我有一个'轻'组件,闪烁会更快?

3 个答案:

答案 0 :(得分:1)

我也遇到了这个问题,但遗憾的是,对我来说,最初的纳维甘没有帮助。但是,无论如何,您可以在此github问题中找到“为什么”发生的详细信息: https://github.com/angular/angular/issues/15716

  

确认。在我的应用程序中,所有路径都是延迟加载的,使用带有默认ViewEncapsulation的css和angular开始在浏览器中使用ng-transition删除标记,此过程需要一秒钟。在引导程序完成后,它会添加样式。   这是http://take.ms/1wizt

的样子

希望这有助于您理解,我仍在尝试在我的应用上解决此问题

答案 1 :(得分:0)

向下滚动到粗体部分以获取答案, 阅读所有内容以了解发生的情况。

关于正在发生的事情的非常简单的解释:

1。)用户转到您的应用程序(或刷新)

2。)服务器在服务器中构建html

3。)它被发送到用户可以看到的浏览器

4。)角度应用程序“重新创建”了该应用程序(就像它是常规的非通用应用程序一样)

5。)发生此更改时,用户会看到闪光灯。

// You can see this by adding:
// You should see a console log in the server
// `Running on the server with appId=my-app-id`
// and then you'll see in the browser console something like
// `Running on the browser with appId=my-app-id`
export class AppModule {
  constructor(
    @Inject(PLATFORM_ID) private platformId: Object,
    @Inject(APP_ID) private appId: string) {
    const platform = isPlatformBrowser(this.platformId) ?
      'in the browser' : 'on the server';
    console.log(`Running ${platform} with appId=${this.appId}`);
  }
}

这是有意的,因为您希望机器人能够提取元标记等。

要删除闪存,您可以做的是将状态从服务器传输到客户端:

您需要将其添加到AppServerModule中的导入中

ServerTransferStateModule

您需要将其添加到您的AppModule:

BrowserTransferStateModule

在引导浏览器应用程序之前更新main.ts文件以侦听DOMContentLoaded:

document.addEventListener('DOMContentLoaded', () => { platformBrowserDynamic().bootstrapModule(AppModule) })

,然后是有关如何转移状态的示例:

import { tap, startWith } from 'rxjs/operators';
import { TransferState, makeStateKey } from '@angular/platform-browser';

const ANIMAL_KEY = makeStateKey<any>('animal');

// omitted ...

    ngOnInit() {
        const id = this.route.snapshot.paramMap.get('name').toLowerCase();
        this.animal$ = this.ssrFirestoreDoc(`animals/${id}`);
    }

    ssrFirestoreDoc(path: string) {
        const exists = this.state.get(ANIMAL_KEY, {} as any);
        return this.afs.doc<any>(path).valueChanges().pipe(
            tap(animal => {
                this.state.set(ANIMAL_KEY, animal)
                this.seo.generateTags({
                title: animal.name,
                description: animal.bio,
                image: animal.imgURL
            });
        }),
        startWith(exists))
    }

我从以下所有方面得到了这些: Angular Universal with FirebaseCode and a more thorough explanation

答案 2 :(得分:0)

@DonDaniel的回答是正确的,但有点过时了。

在Angular 6+中,您可以使用TransferHttpCacheModuleOfficial docs解释了三行更改是如何实现魔术的。

还有一个good article,用于比较旧方法和新方法。