EmberJS Nested Views and Controllers

2019-07-31 23:06发布

我正在写与EmberJS v1.0.pre的应用程序。 我有一个ArrayController它包含了所有的人的名单。 有一堆的展示嵌套的人的意见,他们的宠物和宠物的每一个音符。

|----------------------------------------|
| John                                   | <- Person
|----------------------------------------|
|   Quincy (Dog)                         | <- Pet
|     - Super ornery                     | <- Note
|     - Likes XYZ Dog food               |
|     - Will eat your socks              |
|                                        |
|   Tom (Cat)                            |
|    - Always (not) catching mice        |
|                                        |
|----------------------------------------|
| Roger                                  |
|----------------------------------------|
|   V (Dog)                              |
|    - Likes XYZ Dog food                |
|    - Sneezes, but it's ok              |
|                                        |
|----------------------------------------|
| ...                                    |

从单纯的MVC角度来看感觉应该有每个孩子的控制,但我无法弄清楚如何做到这一点的灰烬。 还有就是上面阵列控制器,然后所有的个人意见。 如果我想删除笔记,或编辑它,好像我需要通过视图的上下文到控制器。

// in the view
click: function () {
  this.get('controller').updateNote(this.get('content'))
}

这种感觉真的对我不好,查看是不是应该对数据的权威来源。 我的假设是,一个ArrayController将实例化一个itemControlerClass与一起itemViewClass

更新:我创建了一个小提琴 ,以更好地说明我的问题。 该功能是故意不完整的,目的是通过点击列表中的某个项目时增加的内容来完成的功能。

UPDATE:对不起,我删除了小提琴事故! 我在做一个最终的解决方案的一些工作,所以我会尝试创建一个新的小提琴瓦特/解决方案。

Answer 1:

“从单纯的MVC角度来看感觉应该为每个孩子控制器”

你并不需要为每个项目的控制,而是对对象的每个集合(人,宠物,债券)的ArrayController。 顺便说一句,在子对象(狗,注释)的任何行动不应该被传递到App.PersonsController 。 这将打破关注点分离原则。

Ember.Router文档包括要在单个对象巢意见的情况下(如/:people_id )。 但是,你要为对象的数组巢意见。 我不能想办法筑巢{{outlet}}的意见,但你可以做到以下几点:

加载的对象的人,宠物,注意在3个ArrayControllers,并委托有关儿童的行动对象到其相应的ArrayController。

App.Router = Ember.Router.extend({
  root: Ember.Route.extend({
    route: '/',
    persons: Ember.Route.extend({
        connectOutlets: function(router) {

          router.get('applicationController').connectOutlet('persons');
          // App.Note.find() fetches all Notes,
          // If you are not using ember-data, make sure the notes are loaded into notesController
          router.set('notesController.content', App.Note.find());
          router.set('petsController.content', App.Pet.find());
        }
    })
  })
});

然后你的people的模板应该是这样的:

{{#each person in people}}
  <h1>My name is {{person.name}}</h1>

  {{#each pet in person.pets}}
     I have a pet with name {{pet.name}}
     <a {{action delete pet target="App.router.petsController">Delete pet</a>
  {{/each}}      

  {{view Ember.TextField valueBinding="myNewPetName" type="text"}}
  <a {{action create myNewPetName person target="controller"}}>
    Add a new pet for this person
  </a>


  {{#each note in person.notes}}
    <!-- delete, create, edit ... -->
  {{/each}}

正如你所看到的,在子对象的动作都被委托给它的控制器(宠物 - > petsController),传递对象作为背景。 在的情况下create行动,控制器需要知道哪些人宠belongsTo 。 因此,我们通过2个上下文:这个人,和宠物(为简单起见,我以为只是一个名称为PET)的特性。

在你App.petsControllers你应该有沿线的行动:

App.PetsController = Ember.ArrayController.extend({
   delete: function(e) {
     var context = e.context;
     this.get('content').removeObject(context);
     // Also, if you use ember-data,
     // App.Pet.deleteRecord(context);
   },

   create: function(e) {
     var petName = e.contexts[0]
     var person = e.contexts[1];
     this.get('content').pushObject({name: petName, person: person});
     // with ember-data:
     // App.Pet.createRecord({name: petName, person: person});
   }
});  


Answer 2:

你应该使用网点。 他们在灰烬的观点有点“占位符”,可以用不同的控制器来处理。

有上面的链接,在那里你已经检查,没有发现任何关于他们一个公平的解释。 但是你回到那个之前,先阅读本: http://trek.github.com/

如果任何这些仍然不能帮助你,让知道,我会放在一起的axample你。



Answer 3:

我想, 这是你的寻找,看看,这是很简单的,你也可以检查这个例子。 基本上你可以实现你想要带插座,路由器用于连接所有网点的行动是什么。



Answer 4:

我是新来的灰烬,并一直在寻找一种方式做同样的事情。 在顶层ArrayController,我只是用itemController属性和它的伟大工作:

App.PeopleController = Ember.ArrayController.extend({
    itemController: "Person"
});

App.PersonController = Ember.ObjectController.extend //...

我的完整的解决方案是在这个js小提琴 。 不幸的是,我得到的方式PetController实例工作似乎哈克给我。



文章来源: EmberJS Nested Views and Controllers