到目前为止,我已成功完成以下任务:
✓HMR(热模块重新加载)设置
✓角度(5)和材料运作良好
✓打开一个对话框(下面的代码片段)
// ...
constructor(private dialog: MatDialog){}
//...
public openDialog(){
this.dialogRef = this.dialog.open(someDialogComponent, {
width: '300px'
});
}
✓在对话框或对话框的父控制器上进行更改
✓MMR被触发(yay)
✖对话挂起死机状态,由于对话框和背景被“卡住”而无法点击,页面基本上被冻结
我试图在父对话控制器中挂钩ngOnInit
和ngOnDestroy
以关闭对话框引用(如果存在),我也试过dialog.closeAll()
,但这有没工作。此外,理想情况下,对话框不必关闭,但我似乎无法修复此僵尸对话框问题。
有没有人遇到过这个?
答案 0 :(得分:4)
我一直在努力解决这个问题,并找到了一个不太理想的解决方案。它在hmr destroy事件期间从DOM中删除任何角度对话框。
const elements = document.getElementsByClassName('cdk-overlay-container');
for (let i = 0; i < elements.length; i++) {
elements[i].innerHTML = '';
}
然后在OnInit中,我们重新创建所有打开的对话框,并传入其数据。唯一的问题是此解决方案保留旧的对话框实例,因此它们不能从后台单击中解除。但是,如果对话框上有一个关闭按钮,则它会正常关闭。 StateService中的OpenDialogs属性可能会更改为完整的componentInstances的TemplateRef [],这可能会解决问题,但我不确定。
无论如何,一个黑客解决方案,直到官方支持对话+ hmr到达。
<强> app.module.ts 强>
export class AppModule {
constructor(private state: StateService, public dialog: MatDialog) { }
OnInit(store) {
if (store !== undefined) {
this.state.SetState(store.State);
for (let i = 0; i < this.state.OpenDialogs.length; i++) {
const t = this.state.OpenDialogs[i].componentInstance;
this.dialog.open(t.constructor, { data: t.data });
}
}
}
OnDestroy(store) {
this.state.OpenDialogs = this.dialog.openDialogs;
store.State = this.state;
const elements = document.getElementsByClassName('cdk-overlay-container');
for (let i = 0; i < elements.length; i++) {
elements[i].innerHTML = '';
}
}
}
<强> state.service.ts:强>
import { Injectable } from '@angular/core';
import { MatDialogRef } from '@angular/material';
@Injectable({
providedIn: 'root'
})
export class StateService {
public OpenDialogs: MatDialogRef<any>[];
constructor() {
}
public SetState(_state: StateService) {
this.OpenDialogs = _state.OpenDialogs;
}
}
<强> main.ts 强>
import { enableProdMode } from '@angular/core';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app/app.module';
import { environment } from './environments/environment';
if (environment.production) {
enableProdMode();
}
// tslint:disable-next-line:no-shadowed-variable
function bootstrap(AppModule) {
return platformBrowserDynamic().bootstrapModule(AppModule)
.then(moduleRef => {
if (environment.hmr) {
if (module['hot']) {
module['hot']['accept']();
if (moduleRef.instance['OnInit']) {
if (module['hot']['data']) {
moduleRef.instance['OnInit'](module['hot']['data']);
}
}
if (moduleRef.instance['OnStatus']) {
module['hot']['apply']((status) => {
moduleRef.instance['OnStatus'](status);
});
}
if (moduleRef.instance['OnCheck']) {
module['hot']['check']((err, outdatedModules) => {
moduleRef.instance['OnCheck'](err, outdatedModules);
});
}
if (moduleRef.instance['OnDecline']) {
module['hot']['decline']((dependencies) => {
moduleRef.instance['OnDecline'](dependencies);
});
}
module['hot']['dispose'](store => {
if (moduleRef.instance['OnDestroy']) {
moduleRef.instance['OnDestroy'](store);
}
moduleRef.destroy();
if (moduleRef.instance['AfterDestroy']) {
moduleRef.instance['AfterDestroy'](store);
}
});
}
}
return moduleRef;
});
}
bootstrap(AppModule);