这是 stackblitz 代码,当使用该service.ts文件进行 API 调用时,我从子组件发出事件。
我的孩子.comp.ts
import { Component, Output,EventEmitter } from '@angular/core';
import {Service} from './service';
@Component({
selector: 'child',
template: `Child data: {{data}}`
})
export class ChildComponent {
@Output() change = new EventEmitter();
data: string;
constructor(private svc: Service){}
ngOnInit(){
this.change.emit(true);
this.svc.getMsg()
.subscribe( data =>{
this.data = data;
this.change.emit(false);
})
}
}
Run Code Online (Sandbox Code Playgroud)
我的app.comp.ts
import { Component ,ChangeDetectorRef} from '@angular/core';
import {Service} from './service';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: [ './app.component.css' ]
})
export class AppComponent {
name = 'Angular 6';
show= false;
constructor(svc: Service,private crd: ChangeDetectorRef){}
showData(event){
this.show = event;
// this.crd.detectChanges(); // this stops the error
}
}
Run Code Online (Sandbox Code Playgroud)
如您所见,添加this.crd.detectChanges();通过告知angular这是需要另一个更改检测的部分来停止错误。
但是,我在 SO上遇到了这个答案,其中这个错误基本上代表了BAD设计。并且使用detectChanges()似乎更像是一种修复,因为我必须明确地编写它。
有人可以帮助我进行GOOD设计,我不必detectChanges()在值将在生命周期中发生变化的地方明确地编写它。
因此,我调查了实施您所写内容的最佳方法应该是什么。我向 Max 提出了同样的问题。我能得出的结论是
Angular 遵循单向数据流,你可以在这里阅读
在您的情况下,您基本上是show在更改CD 中间的值。现在发生的事情是,当 CD 在 DEV 模式下第二次触发时,它发现您已使用EventEmitter. 这与Angular的单向流相矛盾。您的情况可能的解决方案,
使用this.crd.detectChanges()让角知道明确您已经更改了该值,所以角将是一种足以再次运行CD并不会引发任何错误
或者,show在孩子本身中实现行为,而不是违背 Parent -> Child 的流程。
| 归档时间: |
|
| 查看次数: |
913 次 |
| 最近记录: |