从Angular2中的<button>单击事件可观察到

GBa*_*GBa 31 rxjs angular2-observables angular

使用Angular 2从按钮的onclick事件创建observable的首选方法是什么?

我不确定在组件代码中从DOM中获取本机元素是否被认为是最佳实践(我该怎么做?),或者如果还有其他一些我不知道的快捷方式.

Jos*_*vid 39

不要过度思考它.

@ViewChild('button') button;
clicks$:Observable<any>;

ngOnInit() {
  this.clicks$ = Observable.fromEvent(this.button.nativeElement, 'click');
}
Run Code Online (Sandbox Code Playgroud)

  • 注意:如果按钮最初由于* ngIf而隐藏,则按钮将为null。尽管有多种方法可以解决此问题(通过在按钮和平面图/切换图上使用二传手),但它很快就会变得复杂。在这些情况下,最好使用乔恩的答案。 (2认同)
  • 我认为 fromEvent 应该在 ngAfterViewInit 回调中调用,因为在 ngOnInit 中 this.button 仍然未定义...... (2认同)

Gün*_*uer 28

您可以使用Angular2 RxJS中Observable.fromEvent解释的'Observable_1.Observable.fromEvent不是函数'错误

或者只是转发给像这样的观察者

private obs = new Subject();
public obs$ = this.obs.asObservable();

@HostListener('click', ['$event']) 
clickHandler(event){
  this.obs.next(event);
}
Run Code Online (Sandbox Code Playgroud)

要么

<button (click)="obs.next($event)">
Run Code Online (Sandbox Code Playgroud)


Jon*_*Jon 10

@Gunter的例子并不适合我,因为我的编译器没有识别publ.

这是一个对我有用的例子: modal.component.ts

import { Output, Component } from '@angular/core';
import {Subject} from "rxjs/Subject";

export class MyModal{

    private clickStream = new Subject<Event>();

    @Output() observ = this.clickStream.asObservable();

    buttonClick(event:Event){
        this.clickStream.next(event);
    }
}
Run Code Online (Sandbox Code Playgroud)

内部modal.component.html:

<button type="button" class="btn btn-default" (click)="buttonClick($event)">click me</button>
Run Code Online (Sandbox Code Playgroud)


Sim*_*ver 6

如果您尝试使用 @ViewChild 并且您的按钮在初始化时在页面上不可见(由于 *ngIf),则分配将为空。

您可以将 setter 与 @ViewChild 结合使用,并在按钮首次出现时运行您的初始化。

@ViewChild('btnAdd')
set btnAdd(btnAdd: Button) { ... } 
Run Code Online (Sandbox Code Playgroud)

这很快就会变得笨拙和不方便——特别是如果你从中创建一个可观察的流。

混合方式可能如下:

btnAskAnotherClicks$ = new Subject<Event>();

<button mat-flat-button (click)="btnAskAnotherClicks$.next($event)">Ask another question...</button>
Run Code Online (Sandbox Code Playgroud)

这允许您使用点击流来创建链,但如果按钮最初由于 *ngIf 被隐藏,则没有问题。

不喜欢next你的模板?我也不特别。但我没问题async,它们都是实现细节。好吧,这由您决定-)