2013-02-14 3 views
8

Ho cercato ovunque una risposta ma non sono soddisfatto di quello che ho trovato.In Backbone this.model non è definito, perché?

Il problema è che sto facendo un tutorial da Addy Osmani per creare un'app "Todo" in Backbone, ma quando guardo la console, viene visualizzato un errore che dice che this.model is undefined.

Ho anche provato questa risposta SO Backbone model error displayed in console, ma ho ancora lo stesso errore. Per favore dimmi cosa c'è che non va.

A proposito, quali sono this.model o this.collection? Ho un'idea che si riferiscono a Backbone.Model e Backbone.Collection ma come funzionano? Lo sto chiedendo perché in un altro tutorial this.collection e this.model.models non erano definiti, quando ho definito chiaramente lo Model e lo Collection.

Molte grazie

JS:

//Model 
var Todo = Backbone.Model.extend({ 

    defaults: { 
    title: 'Enter title here', 
    completed: true 
    }, 

    validate: function(attrs) { 
    if (attrs.title === undefined) { 
     return 'Remember to enter a title'; 
    } 
    }, 

    initialize: function() { 
    console.log('This model has been initialized'); 

    this.on('change:title', function() { 
     console.log('-Title values for this model have changed'); 
    }); 

    this.on('invalid', function(model, error) { 
     console.log(error); 
    }); 
    } 
}); 

//View 
var TodoView = Backbone.View.extend({ 

    el: '#todo', 
    tagName: 'li', 
    template: _.template($('#todoTemplate').html()), 

    events: { 
    'dbclick label': 'edit', 
    'click .edit': 'updateOnEnter', 
    'blur .edit': 'close' 
    }, 

    initialize: function() { 
    _.bindAll(this, 'render'); 
      this.render(); 

    }, 

    render: function() { 
    this.$el.html(this.template(this.model.toJSON())); 
    this.input = this.$('.edit'); 
    console.log(this.model.toJSON()); 
    return this; 
    }, 

    edit: function() { 
    //do something... 
    }, 

    close: function() { 
    //do something... 
    }, 

    updateOnEnter: function() { 
    //do something... 
    } 
}); 

var todoview = new TodoView(); 
console.log(todoview.el); 

//Collection 
var TodoList = Backbone.Collection.extend({ 
    model: Todo 
}); 

risposta

10

È necessario creare un'istanza di un Model o Collection e passarlo alla vista. Altrimenti, quando il metodo di rendering viene chiamato su TodoView, this.model sarà nullo.

Per esempio, tenta riordinando le ultime righe del codice in questo modo:

//Collection 
var TodoList = Backbone.Collection.extend({ 
    model: Todo 
}); 

var todos = new TodoList(); 

var todoview = new TodoView({model: todos}); 

Da quel punto in poi, è possibile modificare todos (che è un Collection) e la visualizzazione può ascoltare eventi Todos' e ri-rendering di conseguenza.

+1

Potrei sbagliarmi, ma penso che vogliate passare 'todos' nella vista come' collection' e non 'model', in modo da farvi riferimento all'interno della vista come' this.collection' –

3

Non hai detto, ma presumo che l'errore che stai ottenendo si verifichi nel metodo render().

Il problema è che si definisce un nuovo tipo di modello (var Todo = Backbone.Model.extend({...) tuttavia non lo si istanzia mai, né si passa il modello al costruttore di todoview.

Così per lo meno è necessario fare:

var todomodel = new Todo(); 

var todoview = new TodoView({ 
    model: todomodel 
}); 
2

La risposta in altra questione è la risposta alla tua domanda: non stai passando il modello per la vista quando si crea un'istanza della vista.

var model = new Todo(); 
var todoview = new TodoView({model: model}); 

Quando si passa un oggetto al costruttore di una vista, cerca determinate chiavi e le collega direttamente alla vista.

È possibile vedere che guardando Backbone's source e ricerca di viewOptions.

Ecco come si ottiene il this.model e this.collection automaticamente collegato alla vista this.

+1

" La risposta nell'altra domanda è la risposta alla tua domanda "? Allora, perché stai postando? – vault

+2

Per il contesto aggiunto: la domanda è stata fatta anche su 'this.model' e' this.collection'. Sto solo cercando di essere utile. – satchmorun