Modular Controller Structure for Backbone Marionette

Just sharing. I’ve been breaking my noggin in Backbone Marionette so thought I’d share a really good structure I’ve whittled down a bit for creating a modular sidebar element.

It’s not perfect yet, it needs the call to the `auth class` removing and the user’s id either passing in on init or the controller extends a generic class with the user’s deets in it.

As always, comments are v. welcome. Either on JS or the HTML

<span>
<div class="profile-picture-wrapper">
<% if (profile.image && profile.image.file_resizable) { %>
<img src="<%= profile.image.file_resizable.replace('{resize_spec)', 'w_200,h_200,c_fill,g_face') %>" class="profile-panel__image img-responsive" />
<% } %>
</div>
<button class="btn btn-info js__follow-user pre-icon icon-user-plus btn-short"><span>Follow</span></button>
<h5 class="item-view__title js__clickThrough"><div class="username-wrapper"><%= username %></div></h5>
<div class="stats">
<ul>
<li><a href="#" class="icon-users js__myWhoFollowsUser"><span class="num"><%= profile.stats.followers %></span></a></li>
<li><a href="#" class="icon-target js__myWhoDoesUserFollow"><span class="num"><%= profile.stats.following %></span></a></li>
<li><a href="#" class="icon-calendar js__myEvents"><span class="num"><%= profile.stats.events_total %></span></a></li>
</ul>
</div>
<div class="clear"></div>
</span>

<div class="js__who-to-follow-cnt">
<h3>Who to follow&hellip;</h3>
<div class="js__who-to-follow-list"></div>
<a href="#" class="call-to-action">See all users</a>
</div>

view raw
who-to-follow.html
hosted with ❤ by GitHub

/**
* Who to follow module
*/
define(['log', 'app', 'api/auth', 'common/no-items/view', 'common/single/item-view', 'text!events/list/templates/who-to-follow.html', 'text!events/list/templates/who-to-follow-item.html'], function (log, app, auth, NoItemsView, ItemView, templateCnt, templateItem) {
'use strict';
// Each person
var ItemView = ItemView.extend({
tagName: 'li',
template: _.template(templateItem),
triggers: {
click: 'item:click'
}
});
// Collection of people
var CollectionView = Marionette.CollectionView.extend({
itemView: ItemView,
emptyView: NoItemsView,
className: "who-to-follow-wrapper",
tagName: 'ol',
initialize: function () {
var that = this;
// show profile
this.listenTo(this, 'itemview:item:click', function(__item)
{
app.trigger('users:show', __item.model.get('id'));
});
// User unfollow
this.on('itemview:user:unfollow', function (view, id) {
var request = app.request('user:unfollow', id);
request.fail(function () {
view.trigger('unfollow:error');
});
request.done(function () {
view.trigger('unfollow:success');
});
});
// User follow clicks
this.on('itemview:user:follow', function (view, uri) {
var request = app.request('user:follow', uri);
request.fail(function () {
view.trigger('follow:error');
});
request.done(function () {
view.trigger('follow:success');
});
});
this.itemViewOptions = {
templateHelpers: {
type: 'other occurrences'
}
};
}
});
// The Controller's View
var ContainerView = Marionette.Layout.extend({
template: _.template(templateCnt),
collectionOrg: null,
regions: {
whoToFollowView: ".js__who-to-follow-list"
},
events: {
"click .call-to-action": "callToActionClick"
},
callToActionClick: function (e)
{
e.preventDefault();
app.trigger("user:tag:all");
},
onRender: function ()
{
// get our data
var that = this,
collection = app.request('user:search:everything:extended', {anything: "", rank: "buzz", limit: 6});
//
collection.on('fetch:success', function () {
var collectionToUse = collection;
that.collectionOrg = collection;
// randomise them
collection.shuffle();
// removes yourself from the list if you're there
var removeWhere = this.findWhere({id: auth.get('user').id});
collection.remove(removeWhere);
});
// Load the Collection view
this.whoToFollowView.show(new CollectionView({collection: collection}));
}
});
//
return Marionette.Controller.extend({
// ref to it's container view
_whoToFollowCnt: null,
initialize: function(){
// begin
this._whoToFollowCnt = new ContainerView();
},
toRender: function ()
{
return this._whoToFollowCnt;
}
});
});

view raw
who-to-follow.js
hosted with ❤ by GitHub

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s