如何更新 Angular 9 中动态添加的子组件中的值

问题描述

我有一个动态添加子组件的父组件

@Component({
  selector: 'app-parent',template: `<p>Parent:</p><ng-container #dynamic></ng-container>`
})
export class ParentComponent implements OnInit {
  @ViewChild('dynamic',{ read: ViewContainerRef }) vcr: ViewContainerRef;

  constructor(private fr: ComponentFactoryResolver) {
    
  }

  ngOnInit() {
    const factory = this.fr.resolveComponentFactory(HelloComponent);
    const ref = this.vcr.createComponent(factory);
    ref.instance.name = 'World';
  }

}

子组件如下

@Component({
  selector: 'hello',template: `<h1>Hello {{name}}!</h1>`
})
export class HelloComponent {
  @input() name: string;
}

当我在单击按钮时更改 name 的值 (ref.instance.name='Bird'),它不会使用新的 name 值更新子组件视图。 我也尝试过 ref.changeDetectorRef.detectChanges() 但即使这样也不会更新子组件视图。我在网上阅读文章说 changeDetectorRef.detectChanges() 在主机视图上运行,而不是在组件本身上运行。
当name变量的值发生变化时,如何更新子组件视图?

解决方法

更新输入后调用 ref.changeDetectorRef.detectChanges(); 以触发更改检测

ngOnInit() {
    const factory = this.fr.resolveComponentFactory(HelloComponent);
    const ref = this.vcr.createComponent(factory);
    ref.instance.name = 'World';
    ref.changeDetectorRef.detectChanges();  
}
,

视图相关操作只能在调用 ngAfterViewInit 内部或之后进行。 我尝试了您的示例并将您的代码移至 ngAfterViewInit 方法并开始工作。

@Component({
  selector: 'app-root',template: `<p>Parent:</p><ng-container #dynamic></ng-container>`,styleUrls: ['./app.component.less']
})
export class AppComponent implements AfterViewInit {
  title = 'dynamic-child';

  @ViewChild('dynamic',{ read: ViewContainerRef }) vcr: ViewContainerRef;

  constructor(private fr: ComponentFactoryResolver) {
    
  }
  ngAfterViewInit(): void {
    const factory = this.fr.resolveComponentFactory(HelloComponent);
    const ref = this.vcr.createComponent(factory);
    ref.instance.name = 'World';
  }

}