Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

In Backbone this.model is undefined, why?

I've looked everywhere for an answer but wasn't satisfied with what I've found.

The issue is, I'm doing a tutorial from Addy Osmani to make a 'Todo' app in Backbone, but when I look at the console, I get an error saying that this.model is undefined.

I even tried this SO answer Backbone model error displayed in console, but I still get the same error. Please tell me what is wrong.

By the way, what are this.model or this.collection? I've got an idea that they refer to Backbone.Model and Backbone.Collection but how do they work? I'm asking this because in another tutorial this.collection and this.model.models were also undefined, when I've clearly defined the Model and Collection.

Many Thanks

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
});
like image 994
Shaoz Avatar asked Feb 14 '13 01:02

Shaoz


1 Answers

The answer in the other question is the answer to your question: you're not passing the model to the view when you instantiate the view.

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

When you pass an object to a view's constructor, it looks for certain keys and attaches them directly to the view.

You can see which by looking at Backbone's source and searching for viewOptions.

That's how you get the this.model and this.collection automatically attached to the view's this.

like image 62
satchmorun Avatar answered Sep 19 '22 11:09

satchmorun