Angular2:子组件访问父组件 class variable/function
Angular2: child component access parent class variable/function
我在父组件中有一个可能会被子组件更改的变量,父组件将在视图中使用此变量,因此必须传播更改。
import {Component, View} from 'angular2/core';
@Component({selector: 'parent'})
@View({
directives: [Child],
template: `<childcomp></childcomp>`
})
class Parent {
public sharedList = new Array();
constructor() {
}
}
@Component({selector: 'child'})
@View({template: `...`})
class Child {
constructor() {
//access 'sharedList' from parent and set values
sharedList.push("1");
sharedList.push("2");
sharedList.push("3");
sharedList.push("4");
}
}
基本上你不能直接从父级访问变量。你通过事件来做到这一点。组件的输出 属性 对此负责。我建议阅读 https://angular.io/docs/ts/latest/guide/template-syntax.html#input-and-output-properties
如果您将输入 属性 数据绑定与 JavaScript 引用类型(例如,Object、数组、日期等)结合使用,则 parent 和 child 都将引用 same/one object。 parent 和 child 都可以看到您对共享 object 所做的任何更改。
在 parent 的模板中:
<child [aList]="sharedList"></child>
在child中:
@Input() aList;
...
updateList() {
this.aList.push('child');
}
如果你想在构造 child 时将项目添加到列表中,请使用 ngOnInit()
挂钩(而不是 constructor(),因为 data-bound 属性不是在那一点初始化):
ngOnInit() {
this.aList.push('child1')
}
这个 Plunker shows a working example,在 parent 和 child 组件中都有按钮,它们都可以修改共享列表。
请注意,在 child 中您不得重新分配引用。例如,不要在 child 中这样做: this.aList = someNewArray;
如果这样做,那么 parent 和 child 组件将分别引用两个不同的数组。
如果你想共享原始类型(即字符串、数字、布尔值),你可以将其放入数组或 object(即放入引用类型),或者你可以 emit()
来自 child 的事件,只要原始值发生变化(即让 parent 侦听自定义事件,而 child 将有一个 EventEmitter
输出 属性。有关更多信息,请参阅@kit 的回答。)
更新 2015/12/22:Structural Directives 指南中的 heavy-loader
示例使用了我上面介绍的技术。 main/parent 组件有一个 logs
数组 属性 绑定到 child 组件。 child 组件 push()
到该数组,parent 组件显示该数组。
像 NgModel 对 NgForm 做的小把戏怎么样?您必须将 parent 注册为提供者,然后将 parent 加载到 child.
的构造函数中
这样一来,你就不必把 [sharedList]
放在你所有的 children 上了。
// Parent.ts
export var parentProvider = {
provide: Parent,
useExisting: forwardRef(function () { return Parent; })
};
@Component({
moduleId: module.id,
selector: 'parent',
template: '<div><ng-content></ng-content></div>',
providers: [parentProvider]
})
export class Parent {
@Input()
public sharedList = [];
}
// Child.ts
@Component({
moduleId: module.id,
selector: 'child',
template: '<div>child</div>'
})
export class Child {
constructor(private parent: Parent) {
parent.sharedList.push('Me.');
}
}
那么你的HTML
<parent [sharedList]="myArray">
<child></child>
<child></child>
</parent>
您可以在 Angular 文档中找到有关该主题的更多信息:https://angular.io/guide/dependency-injection-in-action#find-a-parent-component-by-injection
Angular2 文档中关于此主题的主要文章是:
https://angular.io/docs/ts/latest/cookbook/component-communication.html#!#parent-to-child
它涵盖以下内容:
使用输入绑定将数据从 parent 传递到 child
截取输入属性随setter
变化
拦截输入 属性 随着 ngOnChanges
的变化
Parent 监听 child 事件
Parent 通过局部变量
与 child 交互
Parent 调用 ViewChild
Parent 和 children 通过服务进行通信
你可以做到
在 parent 组件中声明:
get self(): ParenComponentClass {
return this;
}
在child组件中,引入ParenComponentClass后,声明:
private _parent: ParenComponentClass ;
@Input() set parent(value: ParenComponentClass ) {
this._parent = value;
}
get parent(): ParenComponentClass {
return this._parent;
}
然后在parent的模板中可以做
<childselector [parent]="self"></childselector>
现在从 child 您可以使用
访问 parent 的 public 属性和方法
this.parent
我在父组件中有一个可能会被子组件更改的变量,父组件将在视图中使用此变量,因此必须传播更改。
import {Component, View} from 'angular2/core';
@Component({selector: 'parent'})
@View({
directives: [Child],
template: `<childcomp></childcomp>`
})
class Parent {
public sharedList = new Array();
constructor() {
}
}
@Component({selector: 'child'})
@View({template: `...`})
class Child {
constructor() {
//access 'sharedList' from parent and set values
sharedList.push("1");
sharedList.push("2");
sharedList.push("3");
sharedList.push("4");
}
}
基本上你不能直接从父级访问变量。你通过事件来做到这一点。组件的输出 属性 对此负责。我建议阅读 https://angular.io/docs/ts/latest/guide/template-syntax.html#input-and-output-properties
如果您将输入 属性 数据绑定与 JavaScript 引用类型(例如,Object、数组、日期等)结合使用,则 parent 和 child 都将引用 same/one object。 parent 和 child 都可以看到您对共享 object 所做的任何更改。
在 parent 的模板中:
<child [aList]="sharedList"></child>
在child中:
@Input() aList;
...
updateList() {
this.aList.push('child');
}
如果你想在构造 child 时将项目添加到列表中,请使用 ngOnInit()
挂钩(而不是 constructor(),因为 data-bound 属性不是在那一点初始化):
ngOnInit() {
this.aList.push('child1')
}
这个 Plunker shows a working example,在 parent 和 child 组件中都有按钮,它们都可以修改共享列表。
请注意,在 child 中您不得重新分配引用。例如,不要在 child 中这样做: this.aList = someNewArray;
如果这样做,那么 parent 和 child 组件将分别引用两个不同的数组。
如果你想共享原始类型(即字符串、数字、布尔值),你可以将其放入数组或 object(即放入引用类型),或者你可以 emit()
来自 child 的事件,只要原始值发生变化(即让 parent 侦听自定义事件,而 child 将有一个 EventEmitter
输出 属性。有关更多信息,请参阅@kit 的回答。)
更新 2015/12/22:Structural Directives 指南中的 heavy-loader
示例使用了我上面介绍的技术。 main/parent 组件有一个 logs
数组 属性 绑定到 child 组件。 child 组件 push()
到该数组,parent 组件显示该数组。
像 NgModel 对 NgForm 做的小把戏怎么样?您必须将 parent 注册为提供者,然后将 parent 加载到 child.
的构造函数中这样一来,你就不必把 [sharedList]
放在你所有的 children 上了。
// Parent.ts
export var parentProvider = {
provide: Parent,
useExisting: forwardRef(function () { return Parent; })
};
@Component({
moduleId: module.id,
selector: 'parent',
template: '<div><ng-content></ng-content></div>',
providers: [parentProvider]
})
export class Parent {
@Input()
public sharedList = [];
}
// Child.ts
@Component({
moduleId: module.id,
selector: 'child',
template: '<div>child</div>'
})
export class Child {
constructor(private parent: Parent) {
parent.sharedList.push('Me.');
}
}
那么你的HTML
<parent [sharedList]="myArray">
<child></child>
<child></child>
</parent>
您可以在 Angular 文档中找到有关该主题的更多信息:https://angular.io/guide/dependency-injection-in-action#find-a-parent-component-by-injection
Angular2 文档中关于此主题的主要文章是:
https://angular.io/docs/ts/latest/cookbook/component-communication.html#!#parent-to-child
它涵盖以下内容:
使用输入绑定将数据从 parent 传递到 child
截取输入属性随setter
变化
拦截输入 属性 随着 ngOnChanges
的变化
Parent 监听 child 事件
Parent 通过局部变量
与 child 交互
Parent 调用 ViewChild
Parent 和 children 通过服务进行通信
你可以做到 在 parent 组件中声明:
get self(): ParenComponentClass {
return this;
}
在child组件中,引入ParenComponentClass后,声明:
private _parent: ParenComponentClass ;
@Input() set parent(value: ParenComponentClass ) {
this._parent = value;
}
get parent(): ParenComponentClass {
return this._parent;
}
然后在parent的模板中可以做
<childselector [parent]="self"></childselector>
现在从 child 您可以使用
访问 parent 的 public 属性和方法this.parent