Angular / RxJS - задержка потока до завершения предыдущего потока - PullRequest
0 голосов
/ 24 февраля 2019

Я создаю компонент уведомлений, который должен показывать уведомления пользователю.Когда сразу создается несколько уведомлений, он должен ставить их в очередь.

Прямо сейчас он показывает первое уведомление просто отлично, но после этого он запускает 2 уведомления одновременно (см. Текущий вывод ниже).Он не ждет, пока предыдущее уведомление отобразится, а затем снова будет скрыто, прежде чем отобразить следующее.

notifications.api.ts :

public notifications = new Subject<INotificationEvent>();
public notifications$ = this.notifications.asObservable();

notifications.component.ts :

private finished = new Subject();

constructor(private notifications: NotificationsApi) {}

zip(this.notificationsApi.notifications$, this.notificationsApi.notifications, (i, s) => s).pipe(
  tap(() => {

    if (!this.isActive) {
      this.finished.next();
    }
  }),
  delayWhen(() => this.finished),
  delay(450),
  tap((event: INotificationEvent) => {
    this.notification = event;
    this.isActive = true;
    this.cd.markForCheck();
    console.log(this.notification);
    console.log('showing');
  }),
  delay(this.hideAfter),
  tap(() => {
    this.isActive = false;
    this.cd.markForCheck();
    console.log('closing');
  }),
  delay(450)
).subscribe(() => {
  console.log('finishing');
  this.finished.next();
});

app.component.ts :

let i = 0;
setInterval(() => {
  this.notifications.newNotification({message: `${i}`, theme: 'primary'});
  i++;
}, 2000);

Токовый выход :

{message: "0", theme: "primary"}
showing
closing
finishing
{message: "1", theme: "primary"}
showing
{message: "2", theme: "primary"}
showing
closing
finishing
{message: "3", theme: "primary"}
showing
{message: "4", theme: "primary"}
showing
closing
closing
finishing
finishing
{message: "5", theme: "primary"}
showing
{message: "6", theme: "primary"}

Желаемый вывод :

{message: "0", theme: "primary"}
showing
closing
finishing
{message: "1", theme: "primary"}
showing
closing
finishing
{message: "2", theme: "primary"}
showing
closing
finishing
{message: "3", theme: "primary"}
showing
closing
finishing
{message: "4", theme: "primary"}
showing
closing
finishing
{message: "5", theme: "primary"}
showing
closing
finishing
{message: "6", theme: "primary"}
showing
closing
finishing

Как это исправить?

1 Ответ

0 голосов
/ 24 февраля 2019

Из того, что вы описываете, мне кажется, что вы могли бы достичь того же самого с помощью concatMap и delay.

. В этом примере каждое нажатие кнопки представляет одно уведомление.Каждое уведомление занимает 2 с.Это зависит от того, что вы хотите сделать в обозревателе, но если вам вообще не нужно уведомление, вы можете оставить его пустым (в противном случае вам, вероятно, понадобится startWith).Несколько уведомлений помещаются в очередь внутри concatMap и выполняются одно за другим.

const notification$ = fromEvent(document.getElementsByTagName('button')[0], 'click');

notification$.pipe(
  concatMap(event => of(event).pipe(
    tap(v => console.log('showing', v)),
    delay(2000),
    tap(v => console.log('closing', v)),
  ))
).subscribe();

Демонстрационная версия: https://stackblitz.com/edit/rxjs-nqtfzm?file=index.ts

...