这是我的代码,显示错误,无法读取未定义的属性标题。
父组件
import { Child } from './child.component';
@Component({
selector: 'parent',
})
export class ParentComponet implements OnInit, AfterViewInit {
constructor(){}
@ViewChild(Child) child: Child;
ngAfterViewInit(){
console.log("check data", this.child.title)
}
}
子组件是。
@Component({
selector: 'child',
})
export class ChildComponet {
public title = "hi"
constructor(){}
}
routing.module.ts就像
{
path: "",
component: ParentComponent,
children: [
{
path: '/child',
component: ChildComponent
}
]
}
给出错误是
ERROR TypeError: Cannot read property 'title' of undefined(…)
答案 0 :(得分:11)
我认为您缺少与创建组件相关的'template'或'templateUrl'
ParentComponent
import { ChildComponent } from './child.component'; // {ChildComponent} not {Child} as we are referencing it to the exported class of ChildComponent
@Component({
selector: 'parent',
template: `<child></child>`
})
export class ParentComponet implements OnInit, AfterViewInit {...}
ChildComponent
@Component({
selector: 'child',
template: `<h1>{{ title }}</h1>`
})
export class ChildComponent {...} // Be sure to spell it right as yours were ChildComponet - missing 'n'
更新,根据用户对此线程的说明
已经添加了Stackblitz Demo供您参考(检查控制台)
如果您要访问在父组件的<router-outlet>
下呈现的ChildComponent,可以通过使用(激活)路由器出口的受支持属性来实现:
每当实例化一个新组件时,路由器插座将发出一个激活事件
ParentComponent的模板
@Component({
selector: 'parent',
template: `<router-outlet (activate)="onActivate($event)"></router-outlet>`
})
export class ParentComponent {
onActivate(event): void {
console.log(event); // Sample Output when you visit ChildComponent url
// ChildComponent {title: "hi"}
console.log(event.title); // 'hi'
}
}
根据访问页面的您父母的孩子下的页面
,结果会有所不同如果您访问 Child1Component ,您将获得其实例
Child1Component {title: "hi"}
如果您访问 Child2Component ,您将获得其实例
Child2Component {name: "Angular"}
这些结果将反映在ParentComponent的onActivate(event)控制台上,供您访问
答案 1 :(得分:3)
那不是应该的工作方式。如果您的ChildComponent
模板中有ParentComponent
标签,您将只能在<app-child></app-child>
中获得ParentComponent
。 >
类似这样的东西:
...
<app-child></app-child>
...
但是由于您使用子路由,并且ChildComponent
将加载到router-outlet
的{{1}}中,因此您将无法使用ParentComponent
< / p>
PS:您只能在ViewChild
内访问它,因为ngAfterViewInit
仅在视图加载后才可以安全地实例化:
ViewChild
以下是您的参考资料Working Sample StackBlitz,它说明了两种情况下的情况。
PS::要通过路由获得import { Component, OnInit, ViewChild } from '@angular/core';
import { ChildComponent } from '../child/child.component';
...
@Component({...})
export class ParentComponent implements OnInit {
@ViewChild(ChildComponent) childComponent: ChildComponent;
...
ngAfterViewInit() {
console.log(this.childComponent);
}
}
中的ChildComponent
属性,您必须使用ParentComponent
或以QueryParam的形式在路由中传递ChildProperty,并使用SharedService
尽管这没有多大意义,但是在您的ActivatedRoute
中,您可以拥有一个链接,该链接将通过ChildComponent
属性作为title
传递用户到ChildComponent 。像这样:
queryParam
在您的<a
[routerLink]="['/child']"
[queryParams]="{title: title}">
Go To Child Route With Query Params
</a>
中,可以使用ParentComponent
来访问它,如下所示:
ActivatedRoute
...
import { ActivatedRoute } from '@angular/router';
...
@Component({...})
export class ParentComponent implements OnInit {
...
constructor(
private route: ActivatedRoute,
...
) { }
ngOnInit() {
this.route.queryParams.subscribe(queryParams => {
console.log('queryParams[`title`]', queryParams['title']);
});
...
}
...
}
只需创建一个SharedService
SharedService
的{{1}},即可通过在其上调用private
方法将其显示为BehaviorSubject
。可以通过暴露一个方法(Observable
)来设置其值,该方法实际上将使用更新后的asObservable
值调用setChildProperty
方法:
next
然后可以将其注入到childProperty
和import { Injectable } from '@angular/core';
import { BehaviorSubject, Observable } from 'rxjs';
@Injectable()
export class SharedService {
private childProperty: BehaviorSubject<string> = new BehaviorSubject<string>(null);
childProperty$: Observable<string> = this.childProperty.asObservable();
constructor() { }
setChildProperty(childProperty) {
this.childProperty.next(childProperty);
}
}
中:
在ParentComponent
中设置值:
ChildComponent
然后在您的ChildComponent
中获取值:
import { Component, OnInit } from '@angular/core';
import { SharedService } from '../shared.service';
@Component({
selector: 'app-child',
templateUrl: './child.component.html',
styleUrls: ['./child.component.css']
})
export class ChildComponent implements OnInit {
public title = "hi"
constructor(private sharedService: SharedService) { }
ngOnInit() {
this.sharedService.setChildProperty(this.title);
}
}
答案 2 :(得分:2)
确保在parent.component.html
模板中添加了<child></child>
标签。