I'm trying to store my models into local storage using backone.localStorage. Unfortunately nothing gets stored.
As for as I understand the collection needs only one line
localStorage: new Backbone.LocalStorage("days")
but that doesn't help. If I check the localStorage using Chrome dev tools nothing is stored.
This is my code:
// Filename: app.js
define([
'jquery',
'underscore',
'backbone',
'localStorage'
], function($, _, Backbone){
var initialize = function(){
(function ($) {
var Day = Backbone.Model.extend({
initialize: function() {
this.on("change", this.calculateWorkTime);
this.calculateWorkTime();
},
defaults: {
"date": new Date(),
"fromAm": 0,
"toAm": 0,
"fromPm": 0,
"toPm": 0,
"workTime": 0
},
isValidTime: function(n) {
return !isNaN(parseFloat(n)) && isFinite(n) && parseFloat(n)>0;
},
calculateWorkTime: function() {
var work = 0.0;
if (timeToFloat(this.get("fromAm")) < timeToFloat(this.get("toAm")) ) {
work += timeToFloat(this.get("toAm")) - timeToFloat(this.get("fromAm"));
}
if (timeToFloat(this.get("fromPm")) < timeToFloat(this.get("toPm")) ) {
work += timeToFloat(this.get("toPm")) - timeToFloat(this.get("fromPm"));
}
this.set("workTime", floatToTime(work));
}
});
var DayList = Backbone.Collection.extend({
model: Day,
localStorage: new Backbone.LocalStorage("days")
});
var DataRow = Backbone.View.extend({
tagName: "tr",
template: _.template($('#table-row-day').html()),
events: {
"change .edit-field": "updateModel",
"click #button-delete-day": "deleteDay"
},
initialize: function() {
this.listenTo(this.model, 'destroy', this.remove);
},
render: function() {
this.$el.html(this.template(this.model.toJSON()));
return this;
},
updateModel: function(event) {
var myValue = "leer";
switch (event.currentTarget.id) {
case "table-edit-date":
myValue = this.$('#table-edit-date').val();
this.model.set("date", myValue);
break;
case "table-edit-fromAm":
myValue = this.$('#table-edit-fromAm').val();
this.model.set("fromAm", myValue);
break;
case "table-edit-toAm":
myValue = this.$('#table-edit-toAm').val();
this.model.set("toAm", myValue);
break;
case "table-edit-fromPm":
myValue = this.$('#table-edit-fromPm').val();
this.model.set("fromPm", myValue);
break;
case "table-edit-toPm":
myValue = this.$('#table-edit-toPm').val();
this.model.set("toPm", myValue);
break;
}
this.render();
console.log(this.model.toJSON());
},
deleteDay: function(a, b, c, d) {
this.model.destroy();
}
});
var Days = new DayList;
AppView = Backbone.View.extend({
el: $("body"),
initialize: function () {
this.listenTo(Days, 'add', this.addOne);
this.listenTo(Days, 'all', this.refreshTotal);
this.total = this.$("#total-work");
Days.fetch();
this.refreshTotal();
},
events: {
"click #button-add-day": "addDay"
},
addDay: function () {
var day = new Day({
"date": $("#form-add-date").val(),
"fromAm": $("#form-add-fromAm").val(),
"toAm": $("#form-add-toAm").val(),
"fromPm": $("#form-add-fromPm").val(),
"toPm": $("#form-add-toPm").val()
});
Days.add(day);
},
addOne: function(day) {
var view = new DataRow({model: day});
this.$("#table-body-days").append(view.render().el);
},
refreshTotal: function() {
var work = 0;
Days.each(function($i) {
work += timeToFloat($i.get("workTime"));
});
this.total.html(floatToTime(work));
}
});
function timeToFloat(time) {
var parts = time.split(":");
if (parts.length<2) return 0.0;
return parseFloat(parts[0])+parseFloat(parts[1])/60;
}
function floatToTime(floatValue) {
var fraction = floatValue - Math.floor(floatValue);
var whole = Math.floor(floatValue);
return whole+":"+Math.round(fraction*60.0);
}
var appview = new AppView;
})($);
};
return {
initialize: initialize
};
});
As the comment points out the calls to save are missing. I added them to DataRow.updateModel() and AppView.addDay().
This is the correct code:
// Filename: app.js
define([
'jquery',
'underscore',
'backbone',
'localStorage'
], function($, _, Backbone){
var initialize = function(){
(function ($) {
var Day = Backbone.Model.extend({
initialize: function() {
this.on("change", this.calculateWorkTime);
this.calculateWorkTime();
},
defaults: {
"date": new Date(),
"fromAm": 0,
"toAm": 0,
"fromPm": 0,
"toPm": 0,
"workTime": 0
},
isValidTime: function(n) {
return !isNaN(parseFloat(n)) && isFinite(n) && parseFloat(n)>0;
},
calculateWorkTime: function() {
var work = 0.0;
if (timeToFloat(this.get("fromAm")) < timeToFloat(this.get("toAm")) ) {
work += timeToFloat(this.get("toAm")) - timeToFloat(this.get("fromAm"));
}
if (timeToFloat(this.get("fromPm")) < timeToFloat(this.get("toPm")) ) {
work += timeToFloat(this.get("toPm")) - timeToFloat(this.get("fromPm"));
}
this.set("workTime", floatToTime(work));
}
});
var DayList = Backbone.Collection.extend({
model: Day,
localStorage: new Backbone.LocalStorage("days")
});
var DataRow = Backbone.View.extend({
tagName: "tr",
template: _.template($('#table-row-day').html()),
events: {
"change .edit-field": "updateModel",
"click #button-delete-day": "deleteDay"
},
initialize: function() {
this.listenTo(this.model, 'destroy', this.remove);
},
render: function() {
this.$el.html(this.template(this.model.toJSON()));
return this;
},
updateModel: function(event) {
var myValue = "leer";
switch (event.currentTarget.id) {
case "table-edit-date":
myValue = this.$('#table-edit-date').val();
this.model.set("date", myValue);
break;
case "table-edit-fromAm":
myValue = this.$('#table-edit-fromAm').val();
this.model.set("fromAm", myValue);
break;
case "table-edit-toAm":
myValue = this.$('#table-edit-toAm').val();
this.model.set("toAm", myValue);
break;
case "table-edit-fromPm":
myValue = this.$('#table-edit-fromPm').val();
this.model.set("fromPm", myValue);
break;
case "table-edit-toPm":
myValue = this.$('#table-edit-toPm').val();
this.model.set("toPm", myValue);
break;
}
this.model.save();
this.render();
console.log(this.model.toJSON());
},
deleteDay: function(a, b, c, d) {
this.model.destroy();
}
});
var Days = new DayList;
AppView = Backbone.View.extend({
el: $("body"),
initialize: function () {
this.listenTo(Days, 'add', this.addOne);
this.listenTo(Days, 'all', this.refreshTotal);
this.total = this.$("#total-work");
Days.fetch();
this.refreshTotal();
},
events: {
"click #button-add-day": "addDay"
},
addDay: function () {
var day = new Day({
"date": $("#form-add-date").val(),
"fromAm": $("#form-add-fromAm").val(),
"toAm": $("#form-add-toAm").val(),
"fromPm": $("#form-add-fromPm").val(),
"toPm": $("#form-add-toPm").val()
});
Days.add(day);
day.save();
},
addOne: function(day) {
var view = new DataRow({model: day});
this.$("#table-body-days").append(view.render().el);
},
refreshTotal: function() {
var work = 0;
Days.each(function($i) {
work += timeToFloat($i.get("workTime"));
});
this.total.html(floatToTime(work));
}
});
function timeToFloat(time) {
var parts = time.split(":");
if (parts.length<2) return 0.0;
return parseFloat(parts[0])+parseFloat(parts[1])/60;
}
function floatToTime(floatValue) {
var fraction = floatValue - Math.floor(floatValue);
var whole = Math.floor(floatValue);
return whole+":"+Math.round(fraction*60.0);
}
var appview = new AppView;
})($);
};
return {
initialize: initialize
};
});
Related
I'm trying to create a module using Backbone.js, but I'm getting the error Javascript Error: Uncaught TypeError: autoAuth.View is not a constructor.
Auth.js.erb
(function(app, Auth){
var game = app.module('game');
Auth.View = Backbone.View.extend({
el: '.js-auth',
cssClass: 'auth',
events: {
'click .js-popup': 'popupLogin',
'click .js-login-with-email': 'emailLogin',
'click .js-tos-modal': 'tosModal',
'click .js-privacy-modal': 'privacyModal',
'click .js-auto-login': 'autoLogin'
},
template: Handlebars.compile(
<%= embed('../templates/auth.hbs').inspect %>
),
initialize: function() {
Handlebars.registerPartial('login-buttons',
<%= embed('../templates/login-buttons.hbs').inspect %>
);
},
render: function() {
_.extend(this.options, {
skipOnboarding: game.player.get('skip_onboarding'),
claimableIncentive: game.incentive.get('claimable'),
claimableAmount: game.incentive.get('amount'),
});
this.$el.addClass(this.cssClass);
this.$el.html(this.template(this.options));
growth.urlChangeNotification();
},
popupLogin: function(event) {
event.preventDefault();
event.stopPropagation();
this.validateLogin(_.partial(popupLogin, event));
},
emailLogin: function(event) {
this.validateLogin(_.partial(this.emailAuth, event));
},
autoLogin: function(event) {
this.validateLogin(_.partial(this.autoAuth, event));
},
validateLogin: function(callback) {
if (this.$el.find('#agree-to-tos').is(':checked')) {
callback();
} else {
this.$el.find('.js-tos-error').show();
}
},
emailAuth: function(view_option, value) {
var emailAuth = app.module('emailAuth');
var emailAuthView = new emailAuth.View;
if (_.isString(view_option)) {
emailAuthView.setViewOption(view_option);
if (view_option === 'reset') {
game.user.set('reset_password_token', value);
}
}
emailAuthView.openModal({
allowCancel: view_option !== 'reset'
});
emailAuthView.render();
},
autoAuth: function(view_option, value) {
var autoAuth = app.module('autoAuth');
var autoAuthView = new autoAuth.View;
if (_.isString(view_option)) {
autoAuthView.setViewOption(view_option);
}
autoAuthView.openModal({
allowCancel: view_option !== 'reset'
});
autoAuthView.render();
},
tosModal: function() {
var modal = new Backbone.BootstrapModal({
content: <%= embed('../templates/terms-of-service.hbs').inspect %>
}).open();
},
privacyModal: function() {
var modal = new Backbone.BootstrapModal({
content: <%= embed('../templates/privacy-policy.hbs').inspect %>
}).open();
}
});
})(app, app.module('auth'));
AutoAuth.js.erb
function(app, AutoAuth)(
var game = app.module('game');
AutoAuth.View = ModalView.extend({
view_modes: ['login'],
template: Handlebars.compile(
<%= embed('../templates/auto-auth.hbs').inspect %>
),
events: {
'submit #email-login': 'logIn',
'click #login': function() {
this.setViewOption('login');
this.render();
},
},
genericErrorMessage: 'Oops something went wrong! Please contact support.',
initialize: function(options) {
var self = this;
this.options = options || {};
this.setViewOption('login');
_.bindAl(this, 'login');
game.user.on({
signin_sucess: function(){
self.reloadPage();
},
signin_error: function(data) {
self.options.error = false;
self.setViewOption('login');
var error = 'Unable to sign in with the given email and password.';
if (data && data.error) { error = data.error; }
self.options.signin_error = error;
self.render();
},
})
},
setViewOption: function(view) {
var self = this;
_.each(self.view_modes, function(k) {
self.options[k] = false;
});
self.options[view] = true;
},
render: function(){
this.$el.html(this.template(this.options));
if (mobile) window.scrollTo(0, 1); // hack for modals on mobile
this.delegateEvents();
this.clearErrors();
var authPage = _.chain(this.options)
.pick(function(value, key) { return value; })
.keys()
.value()[0];
growth.urlChangeNotification();
},
logIn: function(e) {
e.preventDefault();
this.options.email = this.$('#login_email').val();
if (!validateEmail(this.options.email)) {
this.options.signin_error = 'Must enter a valid email address.';
this.render();
return;
}
game.user.signIn({
email: this.options.email,
password: this.$('#login_password').val(),
remember_me: true
});
},
reloadPage: function() {
window.location = window.location.href.substr(0, window.location.href.indexOf('#'));
}
});
})(app, app.module('authAuth'));
Do you have this error on the line with var autoAuthView = new autoAuth.View; ?
To create a new instance of autoAuth.View you need to do var autoAuthView = new autoAuth.View();.
autoAuth.View is the class, to call the contructor, and create a new instance, you need to call it with ().
I have a backbone app where the user clicks a button and the a modal is displayed.
On closing the modal I do the following,
$('#myModal').on('hidden.bs.modal', function () {
self.remove();
App.Routes.Application.navigate(App.Routes.Application.previous(), { trigger: true } );
});
The problem is that the modal view is not getting removed, so I click the button to trigger it again, I see 2 modal windows, how can I remove the modal view and then navigate to the route I need?
I have tried ,
$('#myModal').on('hidden.bs.modal', function () {
setTimeout(function() {
self.remove();
}, 500);
App.Routes.Application.navigate(App.Routes.Application.previous(), { trigger: true } );
});
I thought maybe adding a delay between the removal and the navigate would work but nope.
Self is an instance of this view,
App.Views.CreateNewOrganisationView = Backbone.View.extend({
className: 'modal-body',
template: _.template( $('#tpl-new-organisation').html() ),
events: {
"submit .create-organisation" : "createOrganisation",
"click .js-add-member" : "addMember",
"click .js-add-client" : "addClient",
"click .js-add-project" : "addProject",
"click .js-add-team" : "addTeam",
"click .search-results a" : "selectSearchResult",
},
initialize: function() {
this.model = new App.Models.Organisation;
this.render();
},
clean: function() {
console.log("here");
},
render: function() {
//Backbone.Validation.bind(this);
var self = this;
$('#myModal').on('hidden.bs.modal', function () {
setTimeout( function() {
self.remove();
}, 500);
Pops.Routes.Application.navigate(App.Routes.Application.previous(), { trigger: true } );
});
this.$el.html( this.template() ).insertAfter('.modal-header');
this.model.get('members').add(App.Session);
this.model.get('members').first().set({
id: Pops.Session.get('user_id'),
admin: 0
});
var organisationMembersView = new App.Views.GroupsMembersAdminViews({
collection: this.model.get('members')
});
$("#myModal").modal();
return this;
},
addMember: function(e) {
e.preventDefault();
var element = $(e.currentTarget);
this.$('.search').parent().children().show();
this.$('.search').first().remove();
//element.parent().children().hide();
var search = new App.Views.SearchView({
collection: new App.Collections.Users,
type : "users",
merge: false
});
element.parent().prepend(search.render().el);
},
addClient: function(e) {
e.preventDefault();
var element = $(e.currentTarget);
this.$('.search').parent().children().show();
this.$('.search').first().remove();
//element.parent().children().hide();
var search = new Pops.Views.SearchView({
collection: new Pops.Collections.Clients,
type : "clients",
merge: false
});
element.parent().prepend(search.render().el);
},
addProject: function(e) {
e.preventDefault();
var element = $(e.currentTarget);
this.$('.search').parent().children().show();
this.$('.search').first().remove();
//element.parent().children().hide();
var search = new App.Views.SearchView({
collection: new App.Collections.Projects,
type : "projects",
merge: false
});
element.parent().prepend(search.render().el);
},
addTeam: function(e) {
e.preventDefault();
var element = $(e.currentTarget);
this.$('.search').parent().children().show();
this.$('.search').first().remove();
//element.parent().children().hide();
var search = new App.Views.SearchView({
collection: new App.Collections.Teams,
type : "teams",
merge: false
});
element.parent().prepend(search.render().el);
},
selectSearchResult: function(e) {
e.preventDefault();
var element = $(e.currentTarget),
self = this;
switch( element.data('type')) {
case "organisation":
var organisation = new Pops.Models.Organisation({ id: element.data('id')});
organisation.fetch({
success: function() {
self.model.get('organisations').add(organisation);
}
});
break;
case "project":
var project = new App.Models.Project({ id: element.data('id')});
project.fetch({
success: function() {
self.model.get('projects').add(project);
console.log(self.model);
var model = self.model;
self.$('.search').hide();
self.$('button').show();
var projectsDetails = new App.Views.ProjectNamePillView({
model : project
});
self.$('.search').parent().append( projectsDetails.render().el );
self.$('.search').remove();
}
});
break;
// case "workflow":
// break;
case "user":
var member = new App.Models.User({ id: element.data('id')});
member.fetch({
success: function() {
self.model.get('members').add(member);
console.log(self.model);
var model = self.model;
self.$('.search').hide();
self.$('button').show();
var personAvatar = new App.Views.UserInitialsWithAdmin({
model: member
});
self.$('.search').parent().append( personAvatar.render().el);
self.$('.search').remove();
}
});
break;
case "client":
var client = new App.Models.Client({ id: element.data('id')});
client.fetch({
success: function() {
self.model.get('clients').add(client);
var model = self.model;
self.$('.search').hide()
self.$('button').show();
var clientDetails = new App.Views.GroupNameAndAdminsView({
model: client
});
self.$('.search').parent().append( clientDetails.render().el );
self.$('.search').remove();
}
});
break;
case "team":
var team = new App.Models.Team({ id: element.data('id')});
team.fetch({
success: function() {
self.model.get('teams').add(team);
var model = self.model;
self.$('.search').hide()
self.$('button').show();
team.initialize();
var teamDetails = new App.Views.GroupNameAndAdminsView({
model: team
});
self.$('.search').parent().append( teamDetails.render().el );
self.$('.search').remove();
}
});
break;
}
},
remove: function() {
return Backbone.View.prototype.remove.apply(this, arguments);
},
close: function() {
this.unbind();
this.remove();
},
createOrganisation: function(e) {
e.preventDefault();
var element = $(e.currentTarget);
var self = this;
var data = element.serializeJSON();
this.model.save(data, {
success: function() {
if(App.Collections.OrganisationCollection != undefined) {
App.Collections.OrganisationCollection.add(self.model);
}
if(App.Collections._MyOrganisations != undefined) {
App.Collections._MyOrganisations.add(self.model);
}
$("#myModal").modal('hide');
//App.Routes.Application.navigate('#organisations/' . self.model.get())
},
});
}
});
I know Im pretty close to figuring this out. Im trying to filter out my collection based on if favorite eq true. If I console.log - I can see it's doing its job. But it's not updating my view.
Anyone have any idea what I'm missing or doing wrong?
Here is my code:
var Products = Backbone.Model.extend({
// Set default values.
defaults: {
favorite: false
}
});
var ProductListCollection = Backbone.Collection.extend({
model: Products,
url: '/js/data/wine_list.json',
parse: function(data) {
return data;
},
comparator: function(products) {
return products.get('Vintage');
},
favoritesFilter1: function(favorite) {
return this.filter(function(products) {
return products.get('favorite') == true;
});
},
favoritesFilter: function() {
return this.filter(function(products) {
return products.get('favorite') == true;
});
},
});
var products = new ProductListCollection();
var ProductListItemView = Backbone.View.extend({
el: '#wine-cellar-list',
initialize: function() {
products.bind('reset', this.render, this);
products.fetch();
this.render();
},
render: function() {
console.log(this.collection);
var source = $('#product-template').html();
var template = Handlebars.compile(source);
var html = template(this.collection.toJSON());
this.$el.html(html);
return this;
},
});
// Create instances of the views
var productView = new ProductListItemView({
collection: products
});
var CellarRouter = Backbone.Router.extend({
routes: {
'': 'default',
"favorites": "showFavorites",
"purchased": "showPurchased",
"top-rated": "showTopRated",
},
default: function() {
productView.render();
},
showFavorites: function() {
console.log('Favorites');
productView.initialize(products.favoritesFilter());
},
showPurchased: function() {
console.log('Purchased');
},
showTopRated: function() {
console.log('Top Rated');
}
});
$(function() {
var myCellarRouter = new CellarRouter();
Backbone.history.start();
});
There's many mistakes in your code, I'll try to clarify the most I can :
Your collection should be just like this :
var ProductListCollection = Backbone.Collection.extend({
model: Products,
url: '/js/data/wine_list.json',
comparator: 'Vintage' // I guess you want to sort by this field
});
Your view like this :
var ProductListItemView = Backbone.View.extend({
el: '#wine-cellar-list',
initialize: function() {
this.collection.bind('reset', this.full, this);
this.collection.fetch();
},
full: function() {
this.render(this.collection.models);
},
favorites: function(favorite) {
this.render(this.collection.where(favorite)); // here's the answer to your question
},
render: function(models) {
console.log(models);
var source = $('#product-template').html();
var template = Handlebars.compile(source);
var html = template(models.toJSON()); // You may have to change this line
this.$el.html(html);
return this;
},
});
And in your router :
showFavorites: function() {
console.log('Favorites');
productView.favorites(true); // or false, as you like
}
When a new model is added (via "set" function of the collection), I want the model be inserted at the index maintaining sort order, instead at the end.
Thanks
var Ts = (function () {
var Result = Backbone.Model.extend({
idAttribute : 'PAG_ID'
});
var ResultList = Backbone.Collection.extend({
model: Result,
comparator: function(result) {
//console.log(result);
return result.get('SORT_KEY');
},
});
var resultsCollection = new ResultList(data);
data = undefined;
var TableView = Backbone.View.extend({
tagName: 'table',
initialize : function() {
_.bindAll(this, 'render', 'renderRow');
this.collection.on("add", this.renderRow, this);
},
render: function() {
$(this.el).attr('id', 'tsTable').addClass('resulttable');
this.renderHeader(this.collection.shift());
this.collection.each(this.renderRow);
return this;
},
renderHeader : function(model) {
var col=new HeaderView({model:model});
this.$el.append(col.render().$el);
return this;
},
renderRow : function(model) {
var row=new RowView({model:model});
this.$el.append(row.render().$el);
return this;
}
});
var HeaderView = Backbone.View.extend({
tagName: 'tr',
model: resultsCollection.models,
initialize: function() {
this.model.on('change',this.render,this);
},
render: function() {
var html=_.template(colTemplate,this.model.toJSON());
this.$el.html(html);
return this;
}
});
var RowView = Backbone.View.extend({
tagName: 'tr',
initialize: function() {
this.model.on('all',this.render,this);
},
remove: function () {
debug.log("Called remove event on model");
$(this.el).remove();
},
model: resultsCollection.models,
render: function() {
var html=_.template(rowTemplate,this.model.toJSON());
this.$el.html(html);
return this;
},
attributes : function () {
return {
id : this.model.get('PAG_ID')
};
}
});
var tableView = new TableView({collection: resultsCollection});
$("body").append( tableView.render().$el );
resultsCollection.set(initialdata);
resultsCollection.set(someotherdata, {merge: true});
I have changed to as below and it works.Not sure if this is the best implementation
renderRow : function(model) {
var row = new RowView({model:model});
var index = model.get('SORT_KEY') - 1;
row.render().$el.insertAfter(this.$el.find('tr:eq('+ index +')'));
return this;
}
If you provide a comparator function on your collection, Collection.set will perform a silent sort after the new models have been spliced in.
From backbones source http://backbonejs.org/docs/backbone.html:
set: function(models, options) {
var sortable = this.comparator && (at == null) && options.sort !== false;
var sortAttr = _.isString(this.comparator) ? this.comparator : null;
...
if (toAdd.length) {
if (sortable) sort = true;
this.length += toAdd.length;
if (at != null) {
splice.apply(this.models, [at, 0].concat(toAdd));
} else {
push.apply(this.models, toAdd);
}
}
if (sort) this.sort({silent: true});
Here is a fiddle demonstrating that collection.set respects a comparator.
http://jsfiddle.net/puleos/sczV3/
I've manage to put together the below code through various examples, which seems to work okay, but it doesn't seem to preload my data, can anyone please tell me what I'm missing?
App = (function(Backbone, _){
var Note = Backbone.Model.extend(
{
defaults:
{
part1: 'hello',
part2: 'world'
}
});
var TableList = Backbone.Collection.extend({
model: Note
});
var ListRow = Backbone.View.extend(
{
tagName: 'li',
initialize: function()
{
_.bindAll(this, 'render');
},
render: function()
{
$(this.el).html('<span>'+this.model.get('part1')+' '+this.model.get('part2')+'</span>');
return this;
}
});
var ListView = Backbone.View.extend(
{
el: $('#layout_content'),
events:
{
'click button#add': 'addItem'
},
initialize: function()
{
_.bindAll(this, 'render', 'addItem', 'appendItem');
this.collection = new TableList();
this.collection.bind('add', this.appendItem);
this.counter = 0;
this.render();
},
render: function()
{
var self = this;
$(this.el).append("<button id='add'>Add list item</button>");
$(this.el).append("<ul></ul>");
_(this.collection.models).each(function(item){ // in case collection is not empty
self.appendItem(item);
}, this);
},
addItem: function()
{
this.counter++;
var note = new Note();
note.set({part2: note.get('part2') + this.counter});
this.collection.add(note);
},
appendItem: function(item)
{
var listRow = new ListRow({
model: item
});
$('ul', this.el).append(listRow.render().el);
}
});
var app = function(initialModels)
{
this.start = function()
{
this.tableList = new TableList();
this.listView = new ListView({collection: this.tableList});
this.tableList.reset(initialModels);
};
};
return app;
})(Backbone, _);
then init the app with:
<script language="javascript">
var app = new App([{"id":"95","note_title":"can we find the title"},{"id":"93","note_title":"some title"}]);
app.start();
</script>
okay, there are a few issues with your code,
there are 2 issues in your start method,
a) you throw away your collection
this.start = function()
{
this.tableList = new TableList();
this.listView = new ListView({collection: this.tableList});
this.tableList.reset(initialModels);
};
and then in intialize is where you overwrite the collection you pass along
initialize: function()
{
_.bindAll(this, 'render', 'addItem', 'appendItem');
this.collection = new TableList(); // this one gets overwritten, remove this line
}
b) you trigger a collection reset with the models you want to populate it with, but don't listen to an event, either add a listener like this:
this.collection.bind('reset', this.appendAllItems, this);
or create your collection like this:
this.start = function()
{
this.tableList = new TableList(initialModels);
this.listView = new ListView({collection: this.tableList});
};