我有一个检索对象的搜索功能
this.searchForObjectByName = () => {
this.server.get('objects/?searchTerm=' + self.searchTerm)
.then(groupObjects=>
{
this.searchResults = groupObjects;
});
}
然后我将其结果设置为名为searchResults的属性,该属性是一组对象。 我现在想根据结果执行一些过滤。假设我有一些看似如下的对象组:
{
id: 1,
name: 'group 1',
objects: [
{
id: 1,
name: 'object name 1',
categories: ['Cat A', 'Cat B']
},
{
id: 2,
name: 'object name 2',
categories: ['Cat A', 'Cat D']
},
{
id: 3,
name: 'object name 3',
categories: ['Cat C', 'Cat D']
}
]
},
{
id: 2,
name: 'group 2',
objects: [
{
id: 4,
name: 'object name 4',
categories: ['Cat A', 'Cat F']
},
{
id: 5,
name: 'object name 5',
categories: ['Cat C', 'Cat D']
}
]
}
我想过滤以仅显示Cat A对象。 我有一个计算器,根据选定的类别过滤搜索结果:
get filteredSearchResults(): any[] {
var filteredGroups = this.searchResults.map(res => {
let filteredGroup = new Group;
filteredGroup = res.id,
filteredGroup = res.name;
filteredGroup = res.objects.filter(o => this.filteredCategories.some(fc => o.categories.some(oc => oc == fc)));
return filteredGroup;
});
filteredGroups = filteredGroups.filter(fg => fg.objects.length > 0);
return filteredGroups;
}
这会很好地过滤结果,我可以选择不同的类别并正确过滤。然而,它在UI中遍布各处,由于使用计算器来过滤结果,结果会不断更新。我不能使用computedfrom属性,因为它基于我选择的过滤类别(即数组)和从服务器返回的结果(也是数组)。还有其他人以前遇到过这个问题吗?我尝试的所有内容都会导致抖动,我不确定如何以不同的方式做到这一点。
我可以在选定的类别更改时触发事件,或者从服务器返回数据时,我可以重新计算过滤后的结果。这可以工作,但很hacky,并希望能够在计算
中执行此操作答案 0 :(得分:1)
如果没有computedFrom,您的属性获取器将被轮询,这就是您的界面跳转的原因。我不熟悉.some,但我猜不到订单。虽然你可以简单地命令你的搜索结果解决这个问题,但是每隔5秒对数组进行过滤和排序是非常低效的。
使用集合观察器,只有在界面过滤器实际更改时才会执行过滤器代码。 我还没有真正测试过此代码
import { BindingEngine, Disposable, bindable } from 'aurelia-framework';
export class MyPage
{
@bindable searchTerm: string;
filteredSearchResults: any[];
subscription: Disposable;
constructor(private bindingEngine: BindingEngine)
{
}
attached()
{
this.subscription = this.bindingEngine.collectionObserver(this.filteredCategories).subscribe(this.filtersChanged);
}
detached()
{
this.subscription.dispose();
}
searchTermChanged(newValue: string, oldValue: string)
{
this.find();
}
find()
{
this.server.get('objects/?searchTerm=' + this.searchTerm)
.then(groupObjects=>
{
this.searchResults = groupObjects;
this.update();
});
}
update()
{
// your original filtering logic unchanged
var filteredGroups = this.searchResults.map(res =>
{
let filteredGroup = new Group;
filteredGroup = res.id,
filteredGroup = res.name;
filteredGroup = res.objects.filter(o => this.filteredCategories.some(fc => o.categories.some(oc => oc == fc)));
return filteredGroup;
});
filteredGroups = filteredGroups.filter(fg => fg.objects.length > 0);
// set value instead of using a computed property
this.filteredSearchResults = filteredGroups;
}
filtersChanged(splices)
{
this.update(); // you could remove this method and bind the array observable directly to update()
}
}