我怎样才能 select 在 Angular 中动态加载的 html 元素?

How can I select a html element which loaded dynamically in Angular?

我想要 select 动态创建的特定 html 元素。但是创建 html 块的 "list" 变量正在填充 http 请求并且 dom 没有立即加载。我想 select 通过从 url 获得的 id 元素并等于列表项的 id。所以 selected 元素是未定义的,即使我 select ngAfterViewInit 钩子中的元素。我怎样才能select?

HTML

<div id="wrapper">
    <ng-container *ngFor="let item of list">
        <div [id]="item.id">{{item.content}}</div>
    </ng-container>
</div>

TS

list = null;
selectedItemId = null;

ngOnInit() {
    this.selectedItemId = this.activatedRoute.snapshot.params.id;
}

getList() {
    this.http.get('http://api.example.com').subscribe(
        result => this.list = result
    )
}

ngAfterViewInit() {
    const htmlElement= document.getElementById(this.selectedItemId);

    /* Some codes that using htmlElement variable */
}

你可以使用setTimeout(http请求完成后,你的代码被执行,然后你离开区域,Angular 运行检查并添加元素,超时后执行):

this.http.get('http://api.example.com').subscribe(
    result => this.list = result;
    setTimeout(() => console.log(document.getElementById(this.selectedItemId)))
)

如果用@ViewChildren引用HTML元素,可以订阅QueryList.changes事件,当元素出现在DOM时得到通知。

在模板中,在项目元素上设置一个template reference variable

<div id="wrapper">
  <ng-container *ngFor="let item of list">
    <div #itemElement [id]="item.id">{{item.content}}</div>
  </ng-container>
</div>

在代码中,使用该变量名来引用具有 ViewChildren:

的元素
@ViewChildren("itemElement") private itemElements: QueryList<ElementRef>;

ngAfterViewInit() {
  this.itemElements.changes.subscribe(() => {
    console.log("Item elements are now in the DOM!", this.itemElements.length);
    const htmlElement = document.getElementById(this.selectedItemId);
    ...
  });
}

有关演示,请参阅 this stackblitz。请注意,如果只包含一个 div 元素,则 ng-container 不是必需的。您可以将 *ngFor 指令直接应用于该元素。