I am opening the modal from the DetailsView
as follows:
var $ = jQuery = require('jquery'),
Backbone = require('backbone'),
Handlebars = require('handlebars'),
_ = require('underscore'),
skuDetailsTemplate = require("../../templates/sku/SkuDetails.html"),
skuDetailsModel = require('../../models/sku/SkuDetailsModel'),
updateSkuModel = require('../../models/sku/UpdateSkuModel'),
skuUpdateView = require('../../views/sku/UpdateSkuView'),
inventoryForFacilityModel = require('../../models/inventory/InventoryForFacilityModel'),
skuListingModel = require('../../models/sku/listing/SkuListingModel');
var SkuDetailsView = Backbone.View.extend({
el: ".sku-details-container",
tagName: "div",
initialize: function (options) {
var self = this;
this.skuDetailsModel = new skuDetailsModel();
this.inventoryForFacilityModel = new inventoryForFacilityModel();
this.skuListingModel = new skuListingModel();
this.listenTo(self.skuDetailsModel, 'add', self.render);
this.listenTo(self.skuDetailsModel, 'change', self.render);
this.listenTo(self.inventoryForFacilityModel, 'add', self.render);
this.listenTo(self.inventoryForFacilityModel, 'change', self.render);
this.listenTo(self.skuListingModel, 'add', self.render);
this.listenTo(self.skuListingModel, 'change', self.render);
this.sku_id = options.sku_id;
this.skuDetailsModel.set("id", this.sku_id);
this.skuDetailsModel.fetch({});
this.inventoryForFacilityModel.set("id", this.sku_id);
this.inventoryForFacilityModel.fetch({})
this.skuListingModel.set("id", this.sku_id);
this.skuListingModel.fetch({})
},
events: {
"click .openModal": "openUpdateModal",
"click .btnEditSku": "openUpdateModal"
},
openUpdateModal: function (ev) {
var data = { model: this.skuDetailsModel };
var modalView = new skuUpdateView(data);
modalView.show();
},
render: function () {
var self = this;
this.$el.html(skuDetailsTemplate({
skuDetails: self.skuDetailsModel.toJSON(),
inventoryByFacility: self.inventoryForFacilityModel.toJSON(),
skuListing: self.skuListingModel.toJSON()
}));
}
});
module.exports = SkuDetailsView;
ModalView
var UpdateSkuView = Backbone.View.extend({
className: "modal fade",
attributes: {
tabindex: "-1",
role: "dialog",
},
initialize: function (options) {
var self = this;
this.model = options.model;
this.updateSkuModel = new updateSkuModel();
this.template = skuUpdateTemplate;
},
events: {
"click .save": "saveHandler",
"click .closeModal": "close",
"change .clsEdit": "recordModelChange"
},
recordModelChange: function (e) {
var field = e.target.id;
var value = e.target.value;
var res = this.model.toJSON();
var obj = {};
// if (field === "length" || field === "width" || field === "height" || field === "weight" || field === "mrp" || field === "recommended_selling_price") {
// value = parseFloat(value);
// }
obj[field] = value;
obj["id"] = res.records[0].id;
//var res = this.model.toJSON();
this.updateSkuModel.set(obj, { validate: true });
},
saveHandler: function (e) {
//Save logic
var self = this;
e.preventDefault();
var options = {
validate: true,
success: function (model, response) {
self.showSuccessMessage("SKU with id " + response.records[0].id + " updated successfully");
setTimeout(function () {
self.close();
}, 1500);
}
};
this.updateSkuModel.save({}, options);
},
render: function () {
var self = this;
this.$el.html(this.template({
skuDetails: self.model.toJSON()
})).modal()
return this;
},
show: function () {
$(document.body).append(this.render().el);
},
close: function () {
this.$el.remove(".modal fade");
this.$el.modal("hide");
this.$el.empty();
this.undelegateEvents();
}
});
module.exports = UpdateSkuView;
If i open one modal and then close it and then open another instance of the modal it comes over the previous one.
Please help.
My problem:
Vini, your modal view never calls remove http://backbonejs.org/#View-remove either from parent view or from itself.
Modals are pain to keep track of. Exactly for that reason I used Rendering bootstrap modal using backbone
Despite all that! Look at the events you have. You re-render your parent view with out cleaning up the bindings or removing subsequent views.
I sense that
this.listenTo(self.skuListingModel, 'change', self.render);
binds 'click event' every time you re-render / update your "sku" Remove it and see it works.Your close-method must be altered:
Since you are always creating a new modal the old one is unnecessary (garbage)
Solved my issue:
It was because i had multiple instances of my detailsview that the modal was being rendered so many times.
What i did to solve the issue:
Gave a unique
$el
to myDetailsView
You create a modal instance here:
and here you open it.
Modal view can not be garbage collected because it is referenced form another view.
You have to close the modal from the view where you reference it
I use a modalManager class that extend the Backbone.View for use to show modal views. I think your problem is on the close function, you need to hide the modal and then remove it like my hide funtion.