我有一个Object用于管理从后端接收的数据.
它以所有字段启动显示:false,如果我从服务器收到该特定字段,我最终会将其更改为true.
filterGroups(初始):
export let filterGroups: any = {
genericFilters: {
iboId: {
'display': false,
'template': ''
},
iboCode: {
'display': false,
'template': 'text/iboCode'
},
iboName: {
'display': false,
'template': 'text_input_iboName'
},
iboSurname: {
'display': false,
'template': 'text_input_iboSurname'
},
iboRank: {
'display': false,
'template': 'select/multi_iboRank',
},
iboEmail: {
'display': false,
'template': 'text_input_iboEmail'
},
iboNewsletter: {
'display': false,
'template': 'select/simple_iboNewsletter',
},
},
orderFilters: {
iboTotalOrders: {
'display': false,
'template': 'compound/iboTotalOrders',
}
},
peFilters: {
iboTotalPE: {
'display': false,
'template': 'checkbox/iboTotalPE',
}
},
};
在我的模板中,我想拥有与过滤器组一样多的div.在这种情况下,我们有3个过滤器组:genericFilters,orderFilters和peFilters.
一旦我从服务器接收数据(我在构造函数中调用),就会修改此对象.
因此,在我从异步调用中收到数据后,我的filterGroups将如下所示.
filterGroups(在异步调用之后):
export let filterGroups: any = {
genericFilters: {
iboId: {
'display': true,
'template': ''
},
iboCode: {
'display': true,
'template': 'text/iboCode'
},
iboName: {
'display': true,
'template': 'text_input_iboName'
},
iboSurname: {
'display': true,
'template': 'text_input_iboSurname'
},
iboRank: {
'display': false,
'template': 'select/multi_iboRank',
},
iboEmail: {
'display': true,
'template': 'text_input_iboEmail'
},
iboNewsletter: {
'display': false,
'template': 'select/simple_iboNewsletter',
},
},
orderFilters: {
iboTotalOrders: {
'display': true,
'template': 'compound/iboTotalOrders',
}
},
peFilters: {
iboTotalPE: {
'display': false,
'template': 'checkbox/iboTotalPE',
}
},
};
现在,在我的模板中,我有这个:
模板(HTML):
<div *ngFor="let group of filterGroups | keysCheckDisplay">
<div>
<h4>{{group.key}}</h4>
</div>
</div>
而且,很明显,这是我的@Pipe.
@管:
import { PipeTransform, Pipe } from '@angular/core';
import { isNullOrUndefined } from 'util';
@Pipe({name: 'keysCheckDisplay'})
export class KeysCheckDisplayPipe implements PipeTransform {
transform(value, args: string[]): any {
let keys = [];
for (let key in value) {
if (!isNullOrUndefined(value[key])) {
let display = false;
for (let keyChild in value[key]) {
if (!isNullOrUndefined(value[key][keyChild]) && value[key][keyChild]['display'] === true) {
display = true;
break;
}
}
if (display === true) {
keys.push({key: key, value: value[key]});
}
}
}
return keys;
}
}
在这个@Pipe中你可以看到我做了几件事:
>遍历filterGroups对象
>如果存在具有display:child的子项,则检查对象中的每个组.
功能:
我希望这个@Pipe循环遍历我的Object并返回“过滤器组”,它至少包含一个带有display:true的元素.
问题:
@Pipe正在获取filterGroups对象的第一个版本,并且在我从服务器接收数据时忽略了对象发生更改的事实.
如果我修改filterGroups对象的初始值,@ Pipe可以正常工作.
我尝试过的:
>研究,研究,研究
>我将@Pipe更改为inpure,但我讨厌这个解决方案,因为它的性能很差,而且它进入了无限循环.
>我也试过这种方法:
* ngFor =“let filter of filterGroups | async | keysCheckDisplay”.
但它抛出了以下错误:
Error: InvalidPipeArgument: ‘[object Object]’ for pipe ‘AsyncPipe’
可能的解决方案?
>修改@Pipe?
>修改初始对象?
>创建第二个@Pipe以循环第一个Pipe的结果?
我希望它详细而清晰,如果没有,请不要发表评论,要求提供更多细节,我很乐意更新帖子.
先谢谢你了!
最佳答案 仅在数据更改时调用纯管道.这意味着“data”是一个新的对象实例.如果仅修改了对象的内容,则角度更改检测将不会将其识别为更改,并且不会调用管道.
可能的方法
>使管道不纯净:通常是性能负担
>复制对象如:
var tmp = this.data; this.data = {}; Object.assign(this.data, tmp);
>向管道添加其他参数并更新参数值
*ngFor="let item of data | myPipe:counter"
// updated `data`
// this.counter++;