视图中的属性绑定基于2个单独的数据

时间:2013-02-06 09:13:56

标签: ember.js handlebars.js

在我的Ember.js应用程序中的视图控制器中,我有一系列Travel类型和另一个值与当前用户的旅行偏好。

在视图中,我需要根据当前旅行类型是否是用户首选的旅行偏好,为元素添加CSS类。

这是我所拥有的,我似乎无法想到如何将两者联系起来?任何帮助将不胜感激。

为了这篇文章的好处,值被硬编码,但是travelType和travelPreferences来自AJAX调用(并使用Ember Objects)

控制器:

App.IndexController = Em.ArrayController.extend({
    user: {
         travelPreferences: [
              "1", 
              "3"
         ]
    }
    travelTypes: [
         { TravelTypeID: '1', TravelTypeDescription: 'Car' }, 
         { TravelTypeID: '2', TravelTypeDescription: 'Train' }, 
         { TravelTypeID: '3', TravelTypeDescription: 'Walking' }, 
         { TravelTypeID: '4', TravelTypeDescription: 'Bike' }
    ]
});

查看

<ul>
    {{#each travelTypes}}
        <li>{{TravelTypeDescription}}</li>
    {{/each}}
</ul> 

所以在<li>上,如果travelPreferences数组中的ID与travelType的ID匹配,我需要放置class="preferred"

2 个答案:

答案 0 :(得分:2)

首先,我会将常规javascript对象更改为Ember对象,因此我可以使用binging功能:

    user: Ember.Object.create({
        travelPreferences: [
            "1",
            "3"
        ]
    }),
    travelTypes: [
    Ember.Object.create({
        TravelTypeID: '1',
        TravelTypeDescription: 'Car',
        preferred: false
    }),
    Ember.Object.create({
        TravelTypeID: '2',
        TravelTypeDescription: 'Train',
        preferred: false
    }),
    Ember.Object.create({
        TravelTypeID: '3',
        TravelTypeDescription: 'Walking',
        preferred: false
    }),
    Ember.Object.create({
        TravelTypeID: '4',
        TravelTypeDescription: 'Bike',
        preferred: false
    })],

接下来,我会观察当前用户首选项的更改并更新旅行类型的首选属性:

onUserPreferencesChanged: function () {
    var controller = this;
    controller.get('travelTypes').map(function (travelType) {
        travelType.set('preferred', false);
    });
    this.get('user.travelPreferences').map(function (prefId) {
        controller.get('travelTypes').filterProperty('TravelTypeID', prefId).map(function (travelType) {
            travelType.set('preferred', true);
        });
    });
}.observes('user.travelPreferences.@each'),

最后,我会绑定旅行类型列表中每种旅行类型的首选标志。

    <ul> 
        {{#each travelTypes}} 
        <li {{bindAttr class = "preferred"}}>
            {{TravelTypeDescription}} 
        </li>
        {{/each}}
    </ul>

这是一个工作小提琴,将它全部包装起来:http://jsfiddle.net/B4d6K/4/ 阅读有关框架的更多信息并使用绑定和查看机制,您将看到您可以使用它做任何事情。这可能不是最干净的解决方案,也许你会在阅读之后想出更好的东西。

答案 1 :(得分:0)

我最近问了一个类似的问题,就迭代数组然后使用一些条件逻辑来改变项目的反映方式。我提供的答案对我来说非常有用。参见:

Handlebars Helper to insert view into template based on conditional logic

我建议使用ArrayController迭代旅行类型。然后指定itemController(扩展ObjectController)来控制每个元素的显示。 ObjectController可以有一个方法 getTravelTypeClass ,您可以根据某些逻辑为每个旅行类型返回所需的类。