【问题标题】:Ember: Update ObjectController property from ArrayController action?Ember:从 ArrayController 操作更新 ObjectController 属性?
【发布时间】:2015-05-08 20:10:17
【问题描述】:

免责声明:我对 Ember 很陌生。非常愿意接受任何人的任何建议。

我在 ArrayController 中有一个动作,应该设置一个 ObjectController 属性。创建新对象时如何访问正确的上下文来设置该属性?

这是我最近尝试的缩写应用代码:

ChatApp.ConversationsController = Ember.ArrayController.extend({
  itemController: 'conversation',
  actions: {
    openChat: function(user_id, profile_id){
      if(this.existingChat(profile_id)){
        new_chat = this.findBy('profile_id', profile_id).get('firstObject');
      }else{
        new_chat = this.store.createRecord('conversation', {
          profile_id: profile_id,
        });
        new_chat.save();
      }
      var flashTargets = this.filterBy('profile_id', profile_id);
      flashTargets.setEach('isFlashed', true);
    }
  },
  existingChat: function(profile_id){
    return this.filterBy('profile_id', profile_id).get('length') > 0;
  }
});

ChatApp.ConversationController =  Ember.ObjectController.extend({
  isFlashed: false
});

相关模板代码:

{{#each conversation in controller itemController="conversation"}}
  <li {{bind-attr class="conversation.isFlashed:flashed "}}>
    <h3>Profile: {{conversation.profile}} Conversation: {{conversation.id}}</h3>
    other stuff
  </li>
{{/each}}

【问题讨论】:

  • 哦,抱歉,这是一个不必要且含糊的参考。我的意思是应该在调用的操作中设置该属性。我刚刚删除了引用。

标签: ember.js


【解决方案1】:

我不明白为什么您需要一个对象来处理为列表中的所有元素设置属性。让每个项目自己处理好,这意味着components time。

ControllersViews 无论如何都会被弃用,所以你可以这样做:

App.IndexRoute = Ember.Route.extend({
  model: function() {
    return [...];
  }
});

App.ConversationComponent = Ember.Component.extend({
  isFlashed: false,
  actions: {
    // handle my own events and properties
  }
});

在你的模板中

{{#each item in model}}
  {{conversation content=item}}
{{/each}}

因此,每当您向模型中添加项目时,都会创建一个新组件,并且您不必执行 existingChat 逻辑。

【讨论】:

  • 感谢您的帮助!我正在远离对象/数组控制器以使用组件。当我朝着那个方向前进时,我还有几个问题,但我认为值得单独提出一个问题。如果您有时间看一看,我希望您有任何额外的反馈! stackoverflow.com/questions/30294024/…
【解决方案2】:

ArrayControllerItemController are going to be depreciated。由于您是 Ember 的新手,我认为您最好不要使用它们并专注于应用即将发生的变化。

我可以建议您创建某种代理对象来处理您的附加属性(如isFlashed,但也如isCheckedisActive 等)。这个代理对象(实际上是一个代理对象数组)可以看起来像这样(并且是一个计算属性):

proxiedCollection: Ember.computed.map("yourModelArray", function(item) {
  return Object.create({
    content: item,
    isFlashed: false
  });
});

现在,您的模板可能如下所示:

{{#each conversation in yourModelArray}}
  <li {{bind-attr class="conversation.isFlashed:flashed "}}>
    <h3>Profile: {{conversation.content.profile}} Conversation: {{conversation.content.id}}</h3>
    other stuff
  </li>
{{/each}}

最后,但并非最不重要的是,您摆脱了ArrayController。但是,您不会使用 filterBy 方法(因为它只允许一级深度,并且您将拥有代理对象数组,每个代理对象都处理您过滤的一些属性 - 例如 id)。您仍然可以使用显式 forEach 并提供处理设置的函数:

this.get("proxiedCollection").forEach((function(_this) {
  return function(proxiedItem) {
    if (proxiedItem.get("content.profile_id") === profile_id) {
      return proxiedItem.set("isFlashed", true);
    }
  };
})(this));

【讨论】:

    猜你喜欢
    • 2014-01-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-05-27
    • 2014-03-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多