如何在 Angular 9 中从子组件访问父组件

afe*_*eef 5 javascript angular

问题

  • 无法使用 viewContainerRef 进行父子通信。

代码在 Angular 8.2 中运行

 this.viewContainerRef[ '_data' ].componentView.component.viewContainerRef[ '_view' ].component;
Run Code Online (Sandbox Code Playgroud)

错误

错误类型错误:无法读取未定义的属性“componentView”

公共 API https://angular.io/api/core/ViewContainerRef

    this.viewContainerRef.get(0) still i got null
Run Code Online (Sandbox Code Playgroud)

我需要从子组件访问父组件。

吴版

Package                      Version
------------------------------------------------------
@angular-devkit/architect    0.900.7
@angular-devkit/core         9.0.7
@angular-devkit/schematics   9.0.7
@schematics/angular          9.0.7
@schematics/update           0.900.7
rxjs                         6.5.3
Run Code Online (Sandbox Code Playgroud)

无法在 stackblitz 中复制该问题

https://stackblitz.com/edit/angular-testangular9-communicating-x

问题

ViewContainerRef 在 Angular 9 中不起作用

工作视图ContainerRef

在此输入图像描述

ViewConatinerRef 在 Angular 9 中不起作用 在此输入图像描述

任何建议都是非常受欢迎的。

jpa*_*vel 18

您不应该(绝对)访问第三方库的私有成员,以避免遇到麻烦。幸运的是,如果我做对了你想做的事,你可以采取一些措施来避免访问这些私人成员。我将展示 3 个解决方案,其中 2 个是在本答案末尾引用的 stackblitz 上实现的。

假设您有这样的场景:propertyA您出于某种原因想要在子组件中直接访问一个父组件。

父组件:

@Component({
  template: `
    <child></child>
  `
})
export class ParentComponent { propertyA: string; }
Run Code Online (Sandbox Code Playgroud)

案例A:将母体直接注射到孩子体内

@Component({selector: 'child', ...})
export class ChildComp {
  constructor(private _parent: ParentComponent) { this._parent.propertyA = 'some value'; }
}
Run Code Online (Sandbox Code Playgroud)

案例B:让家长了解孩子的情况ViewContainerRef

@Component({selector: 'child', ...})
export class ChildComp {
  constructor(private viewContainerRef: ViewContainerRef) {
    const _injector = this.viewContainerRef.parentInjector;
    const _parent: ParentComponent = _injector.get<ParentComponent>(ParentComponent);  
    this._parent.propertyA = 'some value';
  }
}
Run Code Online (Sandbox Code Playgroud)

这是重要的部分:角度注入器的存在正是为了执行您想要的操作,因此,正确的做法是找出如何找到注入器来为您进行搜索,而不是尝试自己获取对组件的引用。请记住,注入器以层次结构分布,如果注入器无法解析符号,它会要求其父注入器尝试递归地解析它,直到到达根注入器。这导致我们采用第三种方法,直接获取组件的注入器:

情况C:让parent通过child的注入器,直接注入

@Component({selector: 'child', ...})
export class ChildComp {
  constructor(private _injector: Injector) { 
    const _parent: ParentComponent = this._injector.get<ParentComponent>(ParentComponent);  
    this._parent.propertyA = 'some value';
  }
}
Run Code Online (Sandbox Code Playgroud)

情况 B 和 C 之所以有效,是因为您的组件以父-第 n-子关系分布在组件树中,并且在某些时候它们将在声明/导入它们的模块中具有公共注入器。

我修改了你的 stackblitz以显示这两个解决方案(案例 A 用于 a 组件,案例 B 用于 b 组件),

  • 请注意,viewContainerRef.parentInjector 从 Angular 7 开始已弃用,没有替代品。 (4认同)
  • 是否有类似的方法可以在不知道指令类型的情况下访问指令中的主机组件? (2认同)