Javascript 余烬控制器计算属性(对象类型)更新不起作用
我正在尝试将排序属性(Javascript 余烬控制器计算属性(对象类型)更新不起作用,javascript,ember.js,Javascript,Ember.js,我正在尝试将排序属性(sortProperties和sortAscending)与数据列表上的筛选器相结合 我有一个ArrayController和两个操作,一个用于排序,一个用于过滤器。过滤器操作设置过滤器对象的属性,但不重新计算依赖于过滤器的属性 相关控制器代码: App.PostsController = Ember.ArrayController.extend({ filters: Ember.Object.create({}), filteredContent: functio
sortProperties
和sortAscending
)与数据列表上的筛选器相结合
我有一个ArrayController
和两个操作,一个用于排序,一个用于过滤器。过滤器操作设置过滤器
对象的属性,但不重新计算依赖于过滤器
的属性
相关控制器代码:
App.PostsController = Ember.ArrayController.extend({
filters: Ember.Object.create({}),
filteredContent: function () {
var ret = this.get('arrangedContent');
Object.keys(this.filters).forEach(function (name) {
ret = ret.filter(this.filters.get(name));
}, this);
return ret;
// I expect this to cause `filteredContent` to depend on `filters` property
}.property('arrangedContent', 'filters'),
actions: {
sort: function(property, isSorted) {
this.set('sortProperties', [property]);
if (isSorted) {
this.toggleProperty('sortAscending');
} else {
this.set('sortAscending', true);
}
},
filter: function (property, value) {
var filters = this.get('filters');
switch (property) {
case 'id':
// I expect that call to `set` would trigger `filteredContent` property update
filters.get('id') || filters.set('id', function (post) {
return post.get('id') < value;
});
break;
case 'title':
filters.get('title') || filters.set('title', function (post) {
return post.get('title').indexOf(value) !== -1;
});
break;
}
}
}
});
App.PostsController=Ember.ArrayController.extend({
过滤器:Ember.Object.create({}),
filteredContent:函数(){
var ret=this.get('arrangedContent');
Object.keys(this.filters).forEach(函数(名称){
ret=ret.filter(this.filters.get(name));
},这个);
返回ret;
//我希望这会导致'filteredContent'依赖于'filters'属性
}.property('arrangedContent','filters'),
行动:{
排序:函数(属性,isSorted){
this.set('sortProperties',[property]);
如果(已排序){
此.toggleProperty('sortAscending');
}否则{
此.set('sortAscending',true);
}
},
过滤器:函数(属性、值){
var filters=this.get('filters');
交换机(属性){
案件编号:
//我希望调用'set'会触发'filteredContent'属性更新
filters.get('id')| | filters.set('id',函数(post){
return post.get('id')<值;
});
打破
“标题”一案:
filters.get('title')| | filters.set('title',函数(post){
return post.get('title').indexOf(value)!=-1;
});
打破
}
}
}
});
所以,我的问题是为什么filters.set()
不会导致filteredContent
函数运行
所有代码都在这里–您正在更新
过滤器
对象的属性,因此需要观察正在更改的特定对象属性
可以通过显式列出要依赖的属性来实现这一点:
filteredContent: function () {
//...
}.property('arrangedContent', 'filters.id', 'filters.title'),
或者使用一种叫做的速记符号
更新的JSBin:
更新
带有过滤器的新JSBin作为数组:
如果希望在不更新计算属性的情况下不受限制地使用过滤器属性,则可以将configurefilters
用作数组而不是对象。这使您可以使用Ember的阵列观察者功能(在阵列更改时自动更新过滤)
过滤器
现在是一个过滤器对象数组,其形式如下:
{
name: 'name-of-filter',
filter: function(){
// implementation of filter here
}
}
更新filter
以将过滤器对象推送到filters
数组中:
filter: function (property, value) {
var filters = this.get('filters');
console.log("filter", property, value);
switch (property) {
case 'id':
if (filters.findBy('name', 'id') === undefined) {
filters.pushObject({
name: 'id',
filter: function (post) {
return (post.get('id') < value);
}
});
}
break;
case 'title':
if (filters.findBy('name', 'title') === undefined) {
filters.pushObject({
name: 'title',
filter: function (post) {
return post.get('title').indexOf(value) !== -1;
}
});
}
break;
}
}
过滤器:函数(属性、值){
var filters=this.get('filters');
日志(“过滤器”、属性、值);
交换机(属性){
案件编号:
if(filters.findBy('name','id')==未定义){
pushObject过滤器({
名称:“id”,
过滤器:功能(post){
返回(post.get('id')<值);
}
});
}
打破
“标题”一案:
if(filters.findBy('name','title')==未定义){
pushObject过滤器({
姓名:'头衔',
过滤器:功能(post){
return post.get('title').indexOf(value)!=-1;
}
});
}
打破
}
}
更新computed属性以使用新的筛选器对象,并侦听对数组中每个项的更改
filteredContent: function () {
var ret = this.get('arrangedContent');
var filters = this.get('filters');
filters.forEach(function (filterObj) {
ret = ret.filter(filterObj.filter);
}, this);
return ret;
}.property('arrangedContent', 'filters.@each'), // <-- notice the new @each
filteredContent:function(){
var ret=this.get('arrangedContent');
var filters=this.get('filters');
filters.forEach(函数(filterObj){
ret=ret.filter(filterbj.filter);
},这个);
返回ret;
}.property('arrangedContent','filters.@each'),//非常感谢您的回答!如果我想查看一个无限的属性列表(所有属性),该怎么办?除非您编写自己的可观察对象类,否则无法在不明确声明或自己设置观察者的情况下观察每个属性。@gryzzly您可以将定义过滤器的方式更改为ember可以自动观察的方式,例如将单个过滤器对象放入数组中,然后观察。@c4p I tried与array完全相同,不起作用:(这是基于array的版本嘿,太酷了!我认为”过滤器。[]“
实际上就足够了
@each
监视属性,如果属性在从数组中添加/删除时重新计算,这就足够了。@torazaburo不确定我是否理解您的问题–当过滤器
对象的属性发生更改(添加、更新或删除)时,我希望过滤器内容
重新加载@torazaburo噢,那当然更新了jsbin。但问题是filteredContent函数甚至没有运行。
filteredContent: function () {
var ret = this.get('arrangedContent');
var filters = this.get('filters');
filters.forEach(function (filterObj) {
ret = ret.filter(filterObj.filter);
}, this);
return ret;
}.property('arrangedContent', 'filters.@each'), // <-- notice the new @each