angularjs 2 rc4变化检测:检查后表达发生变化
angularjs 2 rc4 Change detection: expression changed after it was checked
从rc1升级到rc4后,我得到以下异常:
表达式在检查后发生了更改。上一个值:"false"。当前值:"true"
在网上研究了这个问题并阅读了我所能阅读的所有内容后,我仍然不知道如何以"有角度"的方式(没有超时等)纠正这个问题。
- 有用的线程:https://github.com/angular/angular/issues/6005
我知道在开发模式更改检测再次运行时,只是为了确保没有任何更改。我也明白,任何改变绑定的东西都"应该触发另一轮变化检测"。
我不明白的是为什么事件发生时不会自动触发新一轮检测,以及如何纠正。
我有一个非常简单的用例。最上面的组件负责显示外部UI。它还包含一个应该隐藏/显示的控件。此行为由激活的管线组件控制。
子实例化通过活动路由(路由器出口)进行,而不是手动进行。
因此,这个最顶端的组件和所有子组件都订阅了共享服务中的事件发射器并发送事件。
最顶端的组件也在其Oninit上订阅了此事件。当它接收到事件时,它会更改一个局部变量。这反映在该组件的html上。
AppComponent
export class AppComponent implements OnInit {
hidePageControls:boolean = true;
constructor(private apiService: ApiService) {}
ngOnInit(): any {
let me = this;
this.apiService.hidePageControls.subscribe(value => me.hidePageControls = value);
}
}
子组件
ngOnInit() {
me.apiService.hidePageControls.emit(false);
}
这背后的原理是,当用户导航到应用程序的不同部分时,会使用不同的组件。然后,这些组件将事件发送到最上面的组件,以显示/隐藏特定控件。
我读过这个问题的可能解决方案,包括setTimeout(),直接调用更改检测等。人们也说我们不应该"对抗"框架,我同意这一点。
因此,请让我知道我认为子组件通知父组件是否是"错误的"角度思维方式,并尽一切努力让我知道这样做的"角度"方式会是什么样子。
编辑
对于这种类型的错误,我找到的唯一解决方案是使用这样的超时:
拆下变化检测器。当事件被手动触发时,触发一轮更改检测。
constructor(private apiService: ApiService, private categoryService: CategoryService, private router: Router, private cd: ChangeDetectorRef) {
this.cd.detach();
}
.
.
.
.
this.apiService.hidePageControls.subscribe(value => {
me.hidePageControls = value;
setInterval(() => {
me.cd.detectChanges();
}, 100);
});
据我所知,这将导致在由于超时而完成额外的开发更改检测运行后进行更改检测。我发现这是一个挑剔的解决方案。
如果有更好的,请告诉我。
我使用了几乎类似的方式来根据子元素决策启用/禁用控制。在角度更新(rc1->rc4)之前,它就像一个符咒。更新后,组件在第一次加载时就开始中断。突破性变化是:
facade:将EventEmitter更改为默认同步(#8761)(e5904f4)
发布的链接
在子组件的初始化过程中,父组件的值在其更改检测回合完成后发生更改。
修复您的问题可能是:
// in apiService
hidePageControls = new EventEmitter(true);
EventEmitter构造函数中的True将强制其为异步
希望能有所帮助。
Angular不喜欢变化检测导致模型变化。
CCD_ 1由变化检测调用。
您可以使用setTimeout()
延迟更改,直到更改检测完成。setTimeout()
导致应用程序范围内的更改检测运行,因此是不可取的。
您可以使用变更检测未调用的另一个生命周期回调
据我记忆所及,ngAfterViewInit
适用于这种情况。
ngAfterViewInit() {
me.apiService.hidePageControls.emit(false);
}
另一种方法是注入ChangeDetectorRef
并显式调用更改检测,以使Angular在抛出更改之前意识到更改:
constructor(cdRef: ChangeDetectorRef) {}
ngOnInit() {
me.apiService.hidePageControls.emit(false);
this.cdRef.detectChanges();
}
- 为什么不't Javascript对我的输入值进行了一些重新检查
- 在单击任何位置时隐藏元素,而不检查每次DOM单击
- 如何检查管道中未定义的项目
- 如何使用量角器检查类名的变化
- JS触发的复选框's已检查属性;t动态变化
- Javascript 不会检查文本输入值是否随组合网格而变化
- 在谷歌地图中检查位置变化
- jQuery:记录数组中的元素变化,并通过索引检查它是如何变化的
- 检查多个变量的值变化
- 检查窗口大小是否有变化和性能/优化
- 如何动态检查Jquery变量是否发生了变化
- 如何检查主干中几个属性的变化
- jQuery检查输入值是否随变化而增加/减少
- DOMSubtreeModified -检查是否只有容器中的第一项发生了变化
- Ionic 2范围滑块导致";表达式值在检查后发生变化";错误
- angularjs 2 rc4变化检测:检查后表达发生变化
- 如何创建 Chrome 扩展程序来检测在线产品列表,并定期检查价格变化
- 如何在每次不触发命令的情况下检查css的变化
- 当文本字段发生变化时,检查表单的有效性,就像gmail注册表单一样
- 有没有一种方法可以在表单发生变化时检查它?