Angular 为什么我能';t访问组件构造函数中的模板DOM元素

Angular 为什么我能';t访问组件构造函数中的模板DOM元素,angular,typescript,rxjs,reactive-programming,Angular,Typescript,Rxjs,Reactive Programming,从RxJS开始,我想创建一个简单的按钮点击流,所以我只需这样做: export class AppComponent { button : HTMLElement = document.querySelector('button'); refreshClickStream$ = Observable.fromEvent(this.button, 'click') .subscribe(); constructor(){ } 但在控制台中接

从RxJS开始,我想创建一个简单的按钮点击流,所以我只需这样做:

export class AppComponent {

    button : HTMLElement = document.querySelector('button');

    refreshClickStream$ = Observable.fromEvent(this.button, 'click')
       .subscribe();

    constructor(){
    }  
但在控制台中接收该错误

我也这样试过:

  clicked(e) {
    return Observable.fromEvent(e.target, 'click')
    .do(console.log)
       .subscribe();
  }
template: `<button #b>...</button>`
...
class AppComponent {
   @ViewChild('b') button;

   ngOnInit() {
       this.refreshClickStream$ = Observable.fromEvent(this.button, 'click').subscribe();
   }
}
但在第一次单击之后,我在控制台中没有得到任何输出。第二次单击后,我得到一个MouseEvent对象。第三次单击后,我得到两个MouseEvent对象。在第四次单击之后,我得到三个,等等。因此我认为单击事件处理程序与RxJS
fromEvent
函数重复


欢迎提供任何解释。

您有以下设置:

AppComponent 
   template: '<button>some button</button>'
   button : HTMLElement = document.querySelector('button');
现在,Angular遍历组件树,为每个组件逐个创建一个具有DOM节点的视图。因此,它首先为托管
应用程序组件的组件创建一个视图。它为它生成一个DOM主机元素,然后调用
AppComponent
构造函数。此时,还没有创建带有按钮DOM元素的
AppComponent
视图。因此,在执行构造函数时,您将尝试查找尚未创建的DOM元素按钮

要实现您想要实现的目标,您可以使用任何生命周期挂钩。要获得更多信息,请阅读我的答案

除了这个问题,我还建议使用
@ViewChild
进行DOM查询和
ngOnInit
生命周期挂钩,如下所示:

  clicked(e) {
    return Observable.fromEvent(e.target, 'click')
    .do(console.log)
       .subscribe();
  }
template: `<button #b>...</button>`
...
class AppComponent {
   @ViewChild('b') button;

   ngOnInit() {
       this.refreshClickStream$ = Observable.fromEvent(this.button, 'click').subscribe();
   }
}
模板:``
...
类AppComponent{
@ViewChild(“b”)按钮;
恩戈尼尼特(){
this.refreshClickStream$=Observable.fromEvent(this.button,'click').subscribe();
}
}

mm myabe您是否尝试过在单击的事件中执行此操作?。但可能在组件的init中执行。。因为我认为每次点击都会有一个新的订阅。同意,我还认为我可能会得到很多订阅。然而,我把这个问题留给了未来,因为那个错误,目前我无法得到任何关于这个的信息流……好吧,现在我聪明多了。非常感谢!你能不能也写-1。为什么建议使用@ViewChild?2.My app component是主要组件,那么它的主机是什么呢?请将view child用于与平台无关的代码。使用它,您不必使用
querySelector
本机浏览器API方法。对于每个条目/根组件,Angular生成一个包装器主机组件。你看不到它,但它就在那里)你可以在chrome调试工具中看到为它生成的工厂
App\u组件\u主机