Angular 2 服务 + RxJS BehaviourSubject 或 EventEmitter

2024-03-17

我是 Angular 2 和 RXJS 的新手。我有一个带有 2 个触发器(按钮)的自定义标头组件,它应该在应用程序的不同部分激活 2 个不同的导航指令。我创建了一个服务,它注册了 2 个不同的导航指令,并且标头组件订阅了该指令。我想知道链接标题中的按钮以根据单击的触发器调用每个指令中的 open() 和 close() 函数的最佳方法是什么。

注意:请注意,我无法使用 ViewChild 或 ContentChild,因为导航可以位于页面上的任何位置。它们可以位于不同的 CustomComponent 中,并且不一定是标头组件的子级。

我能想到两个选择:

  1. 为服务中的 2 个导航指令创建 2 个单独的 Observables/BehaviorSubject,并让标头将打开和关闭消息传递给它们,并使各个导航指令订阅每个相应的 Observables。
  2. 使用 EventEmitters 但我不确定如何使用这种方法。

您能建议一个解决这个问题的好方法吗?

包含导航的自定义组件:

@Component({
  selector: 'my-app',

  template: `
    <h1>{{title}}</h1>
    <my-custom-header>
      This is some text inside the header
    </my-custom-header>
    <nav custom-nav-1>Custom Nav 1</nav>
    <nav custom-nav-2>Custom Nav 2</nav>
  `
})
export class AppComponent {
  title = 'Hello!';
}

标头组件:

@Component({
  selector: 'my-custom-header',

  template: `
    <div class="container">
      This is a header
      <ng-content></ng-content>
      <div>Number of Nav Registered: {{noOfNav}}</div>
      <button type="button" (click)="toggleNav1()">Toggle Nav 1</button>
      <button type="button" (click)="toggleNav2()">Toggle Nav 2</button>
    </div>
  `,
  styles: ['.container { border: 1px solid; }'],
})
export class HeaderComponent {
  title = 'Hello!';
  noOfNav = 0;

  constructor(private navService: NavService) {}

  ngOnInit() {
    this.navService._navSubject.subscribe({
      next: (id) => {
        if(id!=0) {
          this.noOfNav++;
        }
      }
    });
  }

  toggleNav1() {
    console.log("Toggle Nav 1");
  }

  toggleNav2() {
    console.log("Toggle Nav 2");
  }
}

导航服务:

@Injectable()
export class NavService {
  public _navSubject: BehaviodSubject = new BehaviorSubject<number>(0);

  registerNavId(id: number) {
    this._navSubject.next(id);
  }
}

Nav1指令

@Directive({
  selector: '[custom-nav-1]'
})
export class NavDirective1 {
  constructor(private navService: NavService) {}

  ngOnInit() {
    this.navService.registerNavId(1);
  }

  isOpen() {
    console.log("isOpen");
  }

  open() {
    console.log("Open Nav");
  }

  close() {
    console.log("Close Nav");
  }
}

Nav2指令:

@Directive({
  selector: '[custom-nav-2]'
})
export class NavDirective2 {
  constructor(private navService: NavService) {}

  ngOnInit() {
    this.navService.registerNavId(2);
  }

  isOpen() {
    console.log("isOpen");
  }

  open() {
    console.log("Open Nav 2");
  }

  close() {
    console.log("Close Nav 2");
  }
}

笨蛋:https://plnkr.co/edit/3ISyH7ESoNlt65J56Yni?p=preview https://plnkr.co/edit/3ISyH7ESoNlt65J56Yni?p=preview


由于您的组件是松散耦合的(彼此不认识)并且您需要它们之间进行一些交互,因此您的方法(使用 RxJS)是与 angular2 最对应的方法。

现在一切都变成了响应式,甚至是表单。

当您从可重用组件中输出事件时,EventEmitter 很好而且很简单。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Angular 2 服务 + RxJS BehaviourSubject 或 EventEmitter 的相关文章

随机推荐