我正在尝试使用一个HTML select标记在我的Ember.ArrayController子类中设置动态排序,如下所示:
App.ListController = Ember.ArrayController.extend
sortOptions: [{id: 0, text: 'Price High-Low', sortBy: 'pricing', sortAsc: false},
{id: 1, text: 'Price Low-High', sortBy: 'pricing', sortAsc: true},
{id: 2, text: 'Name Ascending', sortBy: 'name', sortAsc: true},
{id: 3, text: 'Name Descending', sortBy: 'name', sortAsc: false}]
currentSortOptionId: 0
sortBy: (->
this.get('sortOptions')[this.get('currentSortOptionId')].sortBy
).property('currentSortOptionId')
# Override
sortProperties: (->
[this.get('sortBy')]
).property('sortBy')
# Override
sortAscending: (->
this.get('sortOptions')[this.get('currentSortOptionId')].sortAsc
).property('currentSortOptionId')
在我的模板中,我有:
Sort by {{view Ember.Select content=sortOptions
optionValuePath="content.id"
optionLabelPath="content.text"
value=currentSortOptionId}}
{{#each listing in controller.arrangeContent}}
...
{{/each}}
更改选择器大部分时间都有效,而始终可用于切换sort属性。但是,排序方向(通过“sortAscending”)属性会混淆,并且似乎有时会抛出一个操作(即使用先前为“sortAscending”选择的值)。
这可能会发生什么?
编辑:这是一个孤立的例子的JSFiddle:http://jsfiddle.net/s9AFr/3/
如果您多次更改排序选择器,您可以说服自己在某些时候错误地排序 ,尤其是在排序的升序/降序功能时。这种情况似乎“滞后”了用户的选择。
答案 0 :(得分:3)
不幸的是,我认为这是由于bug。
基本上现在发生的事情是Ember不希望sortProperties和sortAscending同时改变。在SortableMixin的sortAscendingWillChange
观察者中,我们跟踪sortAscending
的旧值(将其存储在_lastSortAscending
中),然后,在后观察者中,如果sortAscending
确实如此,他们只是flip the arrangedContent
array:
sortAscendingDidChange: Ember.observer('sortAscending', function() {
if (get(this, 'sortAscending') !== this._lastSortAscending) {
var arrangedContent = get(this, 'arrangedContent');
arrangedContent.reverseObjects();
}
}),
当您同时设置sortAscending
和sortProperties
时会出现问题,因为在观察者触发之前sortAscendingWillChange
,保留OLD sortAscending属性的机架,然后因为{{1} }更改后,数组将使用sortProperties
的NEW值进行重新排序(所以此时,所有内容都按照您的预期排序)....但最后sortAscending
观察者会触发,看到sortAscending不同,所以它再次翻转整个数组。
鉴于此错误的原因,我认为解决方法是确保sortAscendingDidChange
和sortAscending
不会同时更改。
因此,我们可以在观察sortProperties
的观察者中设置它,而不是使sortAscending
成为计算属性,而是在下一个运行循环中设置它(因此我们使用currentSortOptionId
)。这样,Ember.run.later
计算属性将首先更改,内容将被排序,然后sortProperties
属性将被设置。