import { AsyncPipe } from "@angular/common"; import { Component } from "@angular/core"; import { takeUntilDestroyed, toObservable } from "@angular/core/rxjs-interop"; import { injectNetwork } from "ngxtension/inject-network"; import { distinctUntilChanged, map, skipWhile, startWith, switchMap, timer, } from "rxjs"; const INDICATOR_TIMEOUT_MS = 2 * 1000; const INDICATOR_TRANSITION_MS = 300; @Component({ standalone: true, selector: "app-network-indicator", imports: [AsyncPipe], template: ` @let isOnline = isOnline$ | async;
{{ isOnline ? "Online" : "Offline" }}
`, styles: ` .indicator { text-align: center; display: none; opacity: 0; transition: opacity ${INDICATOR_TRANSITION_MS}ms ease, display ${INDICATOR_TRANSITION_MS}ms ease allow-discrete; &.visible { opacity: 1; display: block; } } @starting-style { .indicator.visible { opacity: 0; } } `, }) export class NetworkIndicatorComponent { private readonly network = injectNetwork(); protected readonly isOnline$ = toObservable(this.network.online).pipe( skipWhile(Boolean), distinctUntilChanged(), takeUntilDestroyed() ); protected readonly isVisible$ = this.isOnline$.pipe( switchMap(() => timer(INDICATOR_TIMEOUT_MS).pipe( map(() => false), startWith(true) ) ) ); }