# Rendering a large collection using BackboneJS and LoDash

I have a Playlist object which contains many PlaylistItem children. If I have 10,000 children then the UI gets blocked from rendering until all 10,000 children have been processed.

To avoid this, I've created a recursive function wrapped in a setTimeout. This allows a chunk of the playlist to be rendered, allow the UI to update by pausing for setTimeout and then continue to run until it is empty.

Is this a good implementation? Any critiques? I know I still should implement pagination in the long run, but this is for the short term.

render: function () {
this.$el.html(this.template( _.extend(this.model.toJSON(), { // Mix in chrome to reference internationalize. 'chrome.i18n': chrome.i18n }) )); // Group playlistItems into chunks of 200 to render incrementally to prevent long-running operations. var chunkSize = 200; var playlistItemChunks = _.toArray(this.model.get('items').groupBy(function (playlistItem, index) { return Math.floor(index / chunkSize); })); var self = this; this.incrementalRender(playlistItemChunks, function () { self.$el.find('img.lazy').lazyload({
container: self.$el, event: 'scroll manualShow' }); }); return this; }, incrementalRender: function (playlistItemChunks, onRenderComplete) { // Render a chunk: if (playlistItemChunks.length > 0) { var playlistItemChunk = playlistItemChunks.shift(); // Build up the views for each playlistItem. var items = _.map(playlistItemChunk, function(playlistItem) { var playlistItemView = new PlaylistItemView({ model: playlistItem }); return playlistItemView.render().el; }); // Do this all in one DOM insertion to prevent lag in large playlists. this.$el.append(items);

var self = this;
setTimeout(function() {
self.incrementalRender(playlistItemChunks, onRenderComplete);
});

} else {
onRenderComplete();
}

},

• I'm not entirely convinced that setTimeout to control the amount you render is the right way to go here. Your problem is that you're trying to render 10,000 elements at once.. thats way too much information for a human to process. Instead, why not try using paging and / or infinite scrolling? – Dan Oct 13 '15 at 10:57

• I find it more convenient to use ...bind(this) instead of var self = this; - in this case the extra variable is not necessary the code looks better.