Angular 订阅 EventEmitter 但获取现有项目

Angular subscribe to EventEmitter but fetch existing items

我正在尝试构建一个通知组件。为此,我需要通过服务向 NotificationComponent 发送通知。我这样做的方法是使用 EventEmitter 向组件发送通知,但我希望 NotificationComponent 在第一次通过订阅 Observable of Notifications 路由到现有通知时获取现有通知,但它不起作用。查看我的代码,请指出问题或建议替代方法。

目前只显示2号通知的通知(也就是说第一个通知没有到达NotificationComponent但是2号到达)

下面是NotificationService的代码

import { Injectable } from '@angular/core';
import { Notification } from './notification';
import { from } from 'rxjs';
import { Router } from '@angular/router';
import { EventEmitter } from '@angular/core';

@Injectable({
  providedIn: 'root'
})
export class NotificationService {
  private notifications = [];
  addEvent = new EventEmitter();
  removeEvent = new EventEmitter();

  constructor(private router: Router) {
  }

  add(title: string, message: string, expiresInSeconds: number = null) {
    const noti = new Notification();
    noti.title = title;
    noti.message = message;
    this.notifications.push();

    this.addEvent.emit(noti);
    this.router.navigate([{ outlets: {notification: 'notification'}}]);

    if (expiresInSeconds > 0) {
      setTimeout(() => {
        this.removeById(noti.id);
      }, expiresInSeconds * 1000);
    }
  }

  /* get notifications */
  getNotifications() {
    return from(this.notifications);
  }

  /* remove a notification */
  removeById(notificationId) {
    const index = this.notifications.findIndex(n => {
      return notificationId === n.id;
    });
    this.notifications.splice(index, 1);

    this.removeEvent.emit(notificationId);
  }

}

下面是NotificationComponent的代码class

import { Component, OnInit } from '@angular/core';
import { NotificationService } from '../notification.service';
import { Notification } from '../notification';
import { faWindowClose } from '@fortawesome/free-solid-svg-icons';
import { Router } from '@angular/router';

@Component({
  selector: 'app-notifications',
  templateUrl: './notifications.component.html',
  styleUrls: ['./notifications.component.scss']
})
export class NotificationsComponent implements OnInit {
  notifications: Notification[] = [];
  faWindowClose = faWindowClose;

  constructor(private ns: NotificationService,
              private router: Router) {
  }

  ngOnInit() {
    this.ns.getNotifications()
      .subscribe(notifications => {
      this.notifications = notifications;
    });

    this.ns.addEvent
      .subscribe((notification => {
        this.notifications.push(notification);
      }));

    this.ns.removeEvent
      .subscribe((notification => {
        const index = this.notifications.findIndex(n => {
          return n.id === notification.id;
        });
        this.notifications.splice(index, 1);
      }));
  }

  removeNotification(id) {
    this.ns.removeById(id);

    if (this.notifications.length <= 0) {
      this.router.navigateByUrl('/user-panel');
    }
  }
}

以下是NotificationComponent

的模板html
<div *ngIf="notifications.length >= 1"
  class="notification d-flex flex-row-reverse p-0">
  <div *ngFor="let n of notifications"
    class="alert alert-dark mx-1 p-0">

    <div class="d-flex flex-row p-0">
      <div class="flex-item flex-grow-1">
        <h5>{{n.title}}</h5>
      </div>
      <div class="flex-item">
        <button class="btn btn-sm btn-secondary"
          (click)="removeNotification(n.id)">
          <fa-icon [icon]="faWindowClose"></fa-icon>
        </button>
      </div>
    </div>

    <div>{{n.message}}</div>
  </div>
</div>

将 addEvent 转换为 ReplaySubject。您的组件在发出第一个通知后呈现,并且仅在第一个事件消失后才订阅事件。使用 ReplaySubject,您的组件应该获得第一个事件。

addEvent = new ReplaySubject(1);

似乎还有一个小错误

this.notifications.push();

没有通知被推送到数组,调用时会出错removeById