mat-tab - 点击触发涟漪效应但不改变制表符
mat-tab - click triggers ripple effect but not tab change
在我的 angular-electron 应用程序中,我使用 mat-tab-group,在每个选项卡中我加载组件的相同实例。
我有两种创建新标签的方法:
- 通过单击包含 mat-tab-group 的组件中的按钮
- 第二个是通过 IPC 消息触发的。
两种方式调用相同的函数,我将一个新对象推送到一个数组,选项卡是通过 *ngFor 在这个数组上创建的。
效果:
虽然单击按钮创建的 "second" 选项卡行为正常,但通过 IPC ("third") 触发的选项卡却不正常:
点击 "third" 选项卡时会显示涟漪效果,但选项卡上的点击事件 (selectedTabChange) 仅在我第二次点击 [=42= 中的某处时触发].此外,选项卡的内容(包装在 ng-template 中)仅在第二次单击后才会更改。
保存选项卡的组件以及在每个选项卡中实例化的组件都在更改检测中使用推送策略。
我很确定这与 ngZones 有关,但我不确定如何解决这个问题。感谢您的帮助!
动画 Gif 在这里:
switching Tabs
代码HTML:
<mat-icon (click)="MakeTabActive()">build</mat-icon>
<mat-tab-group mat-align-tabs="start" [selectedIndex]="selectedTab" (selectedTabChange)="RegisterTabChange($event)">
<mat-tab *ngFor="let item of openWfTabs">
<ng-template mat-tab-label>
{{item.title}}
<mat-icon class="example-tab-icon" (click)="removeTabHandler(item.uid)">close</mat-icon>
</ng-template>
{{item.uid}}
<app-wf-tabcontent [wfContentElementUID]=item.uid>
</app-wf-tabcontent>
</mat-tab>
</mat-tab-group>
代码 TS:
this._electronService.ipcRenderer.on('to-all', (event, arg) => {
this.MakeTabActive();
});
MakeTabActive(newTab?:any) {
if (!newTab) {
newTab = new WfTab();
}
if (!this.openWfTabs.includes(newTab)) {
this.openWfDocumentElements.push(newTab);
}
for (let i:number = 0; i<this.openWfTabs.length;i++) {
if (this.openWfTabs[i].uid == newTab.uid) {
this.selectedTab = i;
}
}
this.ref.detectChanges();
}
哇,这比我想象的要容易得多:
事实证明,由于订阅了 Electron 服务,代码 运行 在 NgZone 之外并且它留在那里。
我发现是因为我在被调用的函数中插入了这个:
console.log(NgZone.isInAngularZone());
同一个函数返回一次真,一次假,这取决于我如何调用它。
解决方案非常简单:
在订阅电子服务时,我现在这样调用createTab函数:
this.ngZone.run(() => this.createNewTab());
在我的 angular-electron 应用程序中,我使用 mat-tab-group,在每个选项卡中我加载组件的相同实例。
我有两种创建新标签的方法: - 通过单击包含 mat-tab-group 的组件中的按钮 - 第二个是通过 IPC 消息触发的。
两种方式调用相同的函数,我将一个新对象推送到一个数组,选项卡是通过 *ngFor 在这个数组上创建的。
效果:
虽然单击按钮创建的 "second" 选项卡行为正常,但通过 IPC ("third") 触发的选项卡却不正常:
点击 "third" 选项卡时会显示涟漪效果,但选项卡上的点击事件 (selectedTabChange) 仅在我第二次点击 [=42= 中的某处时触发].此外,选项卡的内容(包装在 ng-template 中)仅在第二次单击后才会更改。
保存选项卡的组件以及在每个选项卡中实例化的组件都在更改检测中使用推送策略。
我很确定这与 ngZones 有关,但我不确定如何解决这个问题。感谢您的帮助!
动画 Gif 在这里:
switching Tabs
代码HTML:
<mat-icon (click)="MakeTabActive()">build</mat-icon>
<mat-tab-group mat-align-tabs="start" [selectedIndex]="selectedTab" (selectedTabChange)="RegisterTabChange($event)">
<mat-tab *ngFor="let item of openWfTabs">
<ng-template mat-tab-label>
{{item.title}}
<mat-icon class="example-tab-icon" (click)="removeTabHandler(item.uid)">close</mat-icon>
</ng-template>
{{item.uid}}
<app-wf-tabcontent [wfContentElementUID]=item.uid>
</app-wf-tabcontent>
</mat-tab>
</mat-tab-group>
代码 TS:
this._electronService.ipcRenderer.on('to-all', (event, arg) => {
this.MakeTabActive();
});
MakeTabActive(newTab?:any) {
if (!newTab) {
newTab = new WfTab();
}
if (!this.openWfTabs.includes(newTab)) {
this.openWfDocumentElements.push(newTab);
}
for (let i:number = 0; i<this.openWfTabs.length;i++) {
if (this.openWfTabs[i].uid == newTab.uid) {
this.selectedTab = i;
}
}
this.ref.detectChanges();
}
哇,这比我想象的要容易得多:
事实证明,由于订阅了 Electron 服务,代码 运行 在 NgZone 之外并且它留在那里。
我发现是因为我在被调用的函数中插入了这个: console.log(NgZone.isInAngularZone());
同一个函数返回一次真,一次假,这取决于我如何调用它。
解决方案非常简单:
在订阅电子服务时,我现在这样调用createTab函数: this.ngZone.run(() => this.createNewTab());