bodokaiser
bodokaiser

Reputation: 15752

Cache backbone views with its events

I am working on a relatively big application which is like some sort of app collection.

All of my apps got a bootstrapping view which loads the base layout and the nested views.

I now started to implement a singleton pattern to the views:

var SomeView = Backbone.View.extend({});

if (SomeView._instance) return SomeView._instance;

SomeView._instance = new SomeView();

return SomeView._instance;

Now I mentioned that when I switch between different apps (views) the event system is broken. This is actually quite logic finally we remove the view out of the document. However I have some sort of resistance against always building up the views new. This is quite ineffective: Everything has to get reloaded (data), and rebuilt.

So is there a way to rebind events to a cached views or is this whole idea bad and I should accept that views have to get rebuilt?

Update:

define(['jquery', 'underscore', 'backbone', 'views/settings/profile'], function($, _, Backbone, ProfileSettingsView) {

    var ContentView = Backbone.View.extend({

        tagName: "div",

        className: "content well",

        initialize: function() {
            this.on('change:section', this.change, this);

            this.views = {};
            this.views.profile = new ProfileSettingsView();
        }, 

        render: function() {
            this.$el.empty();

            return this;
        },

        events: {
            "click": "click"
        },

        // the router triggers this one here
        change: function(query) {
            console.log(query);

            // if I uncomment this then nothing is rendered at all
            //this.$el.detach();

            var el;
            if (query === 'profile') {
                el = this.views.profile.render().el;
            } else {
                this.$el.empty();
            }
            
            if (el) {
                this.$el.empty().append(el);
            }

        },

        click: function(e) {
            console.log('clicked, content should disapear');
        }

    });

    if (ContentView._instance) return ContentView._instance;

    ContentView._instance = new ContentView();

    return ContentView._instance;

});

I am a bit confused about how I can use jQuery's detach(). I looked at the demo in the official docs and found out that it is not enough to call .detach() on a jQuery object. .detach returns a new object which looks like a jQuery one and contains the events bound. The hard thing about this is that I have to save this returnment of detach() somewhere and I have to now from who it's coming. And now I don't have any look through. I will now search for some Backbone.View example using detach() but I think it is to specific....

Update2:

Yes! I found a workaround: Instead of saving the events and then reinserting it in to the DOM. We can just call this.delegateEvents() to rebind all events. This truly is just a workaround and I would be happy if somebody could provide me an example :)

Upvotes: 3

Views: 2075

Answers (1)

Derick Bailey
Derick Bailey

Reputation: 72878

Personally, I prefer to rebuild my views.

However, I know a lot of people that prefer to re-use them. In that case, follow the instructions in this blog post from Tim Branyen: http://tbranyen.com/post/missing-jquery-events-while-rendering

Upvotes: 2

Related Questions