我有一个组件客户管理,其中我正在显示客户列表,单击查看按钮,我导航到另一个我在选项卡中显示的组件客户详细信息。客户详细信息组件上显示以下错误
ERROR Error: ViewDestroyedError: Attempt to use a destroyed view: detectChanges
at viewDestroyedError (core.js:20452)
at Object.debugUpdateDirectives [as updateDirectives] (core.js:23908)
at checkAndUpdateView (core.js:23307)
at callWithDebugContext (core.js:24177)
at Object.debugCheckAndUpdateView [as checkAndUpdateView] (core.js:23879)
at ViewRef_.push../node_modules/@angular/core/fesm5/core.js.ViewRef_.detectChanges (core.js:21688)
at ngx-bootstrap-dropdown.js:639
at HTMLDocument.<anonymous> (platform-browser.js:993)
at ZoneDelegate.push../node_modules/zone.js/dist/zone.js.ZoneDelegate.invokeTask (zone.js:423)
at Object.onInvokeTask (core.js:17290)
答案 0 :(得分:1)
在所有这些烦恼中,要更新UI时可以使用以下方法。这是变更检测的更好的实现,希望在Angular文档中有提及。
detectChanges () {
setTimeout(() => {
if ( this.cdRef !== null &&
this.cdRef !== undefined &&
! (this.cdRef as ViewRef).destroyed ) {
this.cdRef.detectChanges();
}
}, 250);
}
答案 1 :(得分:0)
通常,当您在组件内部订阅触发更改检测的外部Observable时,会发生这种情况。当您不退订销毁组件时,Observable便会触发,并尝试对不再存在的组件进行更改检测。
典型示例:
@Component({...})
class MyComponent {
Input() myTrigger$: Observable<any>;
constructor(private cdr: ChangeDetectorRef) {
}
ngOnInit() {
this.myTrigger$.subscribe(() => {
// do anything useful...
this.cdr.detectChanges(); // <- This call fails, once the component is destroyed
});
}
}
此示例中的解决方案是保留订阅引用,并在销毁时取消订阅。 您不仅应该为变更检测器执行此操作,而且还应该避免一般的严重内存泄漏:
@Component({...})
class MyComponent {
Input() myTrigger$: Observable<any>;
private sub: Subscription;
constructor(private cdr: ChangeDetectorRef) {
}
ngOnInit() {
this.sub = this.myTrigger$.subscribe(() => { // <- keep the subscription for later
...
});
}
ngOnDestroy() {
this.sub.unsubscribe(); // <- unsubscribe on destroy
}
}