在嵌套组件中调用方法

Call a method in the nested component

我有两个组件 (1-app-student-list 2-app-student-detail).

我想在 student-list 中使用 student-detail,如下所示:

app-学生-detail.html

<p>Student Detail Component is here ....</p>

app-学生-detail.ts

export class StudentDetailComponent {
  showDetail() {
    alert("We are in student-detail...");
  }
}

app-学生-list.html

<p>Student List Component is here ....</p>
<app-student-detail></app-student-detail>

app-学生-list.ts

export class StudentListComponent implements OnInit {

  @ViewChild(StudentDetailComponent, { static: true }) studentDetail: StudentDetailComponent;
  constructor() { }

  ngOnInit() {
  }

  showDetail() {
    this.studentDetail.showDetail();
  }

}

showDetail方法中我想调用StudentDetailComponent的方法showDetail

最后,我想在 AppComponent 中使用学生列表

app.component.ts

export class AppComponent {
  public isShow = false;

  @ViewChild(StudentListComponent, { static: true }) studentList: StudentListComponent;
  title = 'AngualrViewChild';

  showDetail() {
    this.isShow = true;
    this.studentList.showDetail();
  }

}

app.component.html

<p>App Component is here ....</p>
<app-student-list *ngIf="this.isShow"></app-student-list>

<hr />
<button type="button" (click)="this.showDetail()">
    Show Detail
</button>

当我调用 StudentListComponentshowDetail 方法时,出现以下错误:

AppComponent.html:6 ERROR TypeError: Cannot read property 'showDetail' of undefined

注意:当我删除上面的ngIf时它会完美地工作

Stackblitz is here

如果您的学生列表未显示(您的 *ngIf 计算结果为 false),那么您的 StudentList 也不会 rendered/available 任何地方。

因此,您的 ViewChild 无法解析任何内容,调用 "this.studentList.showDetail();" 将无效。是的,您将布尔值更改为 true,但 changeDetection 可能没有足够的时间 运行 并实际呈现您的 StudentList。

在您的 App.Component 中,您还应该重新考虑您的 :

{ static: true }

您的视图child目前远非静态,因为它取决于 *ngIf 来解析。将其设置为 "static: true" 将阻止您的 ViewChild 在您的 StudentList 实际可用时更新。

.

这里有两种选择。

  1. (肮脏的解决方法)将您的布尔值切换为 true,让您​​的 *ngIf 执行正确的更改(显示您的 StudentList),然后像这样调用您的 showDetails 方法:

  1. (清洁器)如果您希望在您的 StudentList 可用时立即调用一个函数,您可以在 StudentList.component 中实现 AfterViewInit() 并调用您的函数。

例如:

import { Component, OnInit, AfterViewInit, ViewChild } from '@angular/core';

两者都应该给你你期望的结果,但在从 parent 组件调用 child 组件函数之前,想想你为什么要这样做。

你真的想让 parent 触发对 children 的操作,还是想让 children 在达到某个生命周期后做某事?大多数时候,逻辑可以在 children 中实现,您的 parent 组件只关心渲染 child 或隐藏它。