2013-03-20 65 views
9

Tôi có một bộ sưu tập Động vật.Bộ sưu tập xương sống của mô hình đa hình

App.Collections.Animals extends Backbone.Collection 
    model: App.Animal 
    url: '/animals/' #returns json 

Và các lớp động vật:

App.Models.Animal extends Backbone.Model 

App.Models.Monkey extends App.Models.Animal 
    defaults:{type:'Monkey'} 

App.Models.Cat extends App.Models.Animal 
    defaults:{type:'Cat'} 

App.Models.Dog extends App.Models.Animal 
    defaults:{type:'Dog'} 

Khi bộ sưu tập được làm đầy với JSON (hồ sơ chứa loại thuộc tính) Tôi muốn mô hình được khởi tạo như các mô hình tiểu phân loại (Khỉ, Cát, Chó) và không phải là Động vật. Làm thế nào bạn có thể đạt được điều này?

Trả lời

12

Từ Backbone documentation:

Một bộ sưu tập cũng có thể chứa mô hình đa hình bằng cách ghi đè khách sạn này với một hàm trả về một mô hình.

var Library = Backbone.Collection.extend({ 

    model: function(attrs, options) { 
    if (condition) { 
     return new PublicDocument(attrs, options); 
    } else { 
     return new PrivateDocument(attrs, options); 
    } 
    } 

}); 
0

Ghi đè bộ sưu tập xương sống _prepareModel. Bộ sưu tập mới sử dụng các lớp con khi được định nghĩa khác sử dụng mô hình mặc định.

class App.Collections.Animals extends Backbone.Collection 

model: App.Models.Animal 

_prepareModel: (attrs, options) -> 
    if attrs instanceof Backbone.Model 
    attrs.collection = @ 
    return attrs 

    options || (options = {}) 
    options.collection = @ 
    model_class = APP.Models[attrs.ntype] or this.model 
    model = new model_class(attrs, options) 
    if (!model._validate(attrs, options)) 
    false 
    else 
    model 
6

Giải pháp là đơn giản (tha thứ JS, tôi không biết CoffeeScript):

var SmartZoo = Backbone.Collection.extend({ 
    model: function (attrs, options) { 
     // This code assumes that the object looks something like '{ type: "Cat", ... }'. 
     switch (attrs.type) { 
      case 'Cat': 
       return new Cat(attrs, options); 
      case 'Dog': 
       return new Dog(attrs, options); 
      default: // Unknown subclass 
       return new Animal(attrs, options); 
     } 
    } 
}); 

Bạn cần phải:

  1. Bao gồm một thuộc tính trong mô hình của bạn từ mà bạn có thể suy ra loại mô hình Backbone để tạo ra. Trong ví dụ này, các đối tượng của tôi chứa một thuộc tính được gọi là "type" có giá trị là tên đầy đủ của loại Backbone đại diện cho nó. Hãy chắc chắn để đặt nó trong các giá trị mặc định hoặc khởi tạo Mô hình của bạn để bạn cũng có thể thêm các cá thể mô hình thực vào bộ sưu tập.
  2. Xác định thuộc tính mô hình của bộ sưu tập của bạn dưới dạng hàm. Tham số đầu tiên của hàm này sẽ là đối tượng JS thô (nếu đó là những gì bạn truyền vào) hoặc đối tượng thuộc tính của mô hình Backbone. Dù bằng cách nào, bạn có thể truy cập trường loại của bạn dưới dạng thuộc tính của đối tượng này.
  3. Thực thi logic của bạn để suy ra mô hình thích hợp từ trường loại của bạn.
  4. Trả về phiên bản của mô hình chính xác từ chức năng mô hình.

Đây là một JSFiddle cho thấy bộ sưu tập đa hình này trong hành động: http://jsfiddle.net/FiddlerOnTheTarmac/uR2Sa/

+0

Chỉ cần lưu ý rằng nếu bộ sưu tập có thể có rất nhiều mô hình 'nếu(); nếu không; else' là biểu hiện nhiều hơn 'chuyển đổi' – seebiscuit

Các vấn đề liên quan