Abstracting UI Components with Marionette.View

1,667 views
Skip to first unread message

Elan Hami

unread,
Oct 17, 2013, 10:01:25 AM10/17/13
to backbone-...@googlegroups.com
Hi,

Recently I was involved in a very large project that involved multiple teams developing on the front end.
We used Marionette as our framework and were very happy with it.

One issue we dealt with a lot was creating reusable UI components that would be consistent throughout the project. 
Components could be very simple elements - like buttons, input fields, etc. - or very complex - like a color-picker.
Essentially, these components would be used in order to create views very simply. By reducing a view to a container that aggregates these components, and adds some specifics,  it becomes easy to create new pages.
We wanted to avoid having our templates full of multiple CSS classes, (e.g <a class="my-btn btn btn-primary btn-large .../>).
We also wanted to avoid duplication of the same options passed to many jQuery UI widgets (e.g. datepicker options). Moreover, many jQuery widgets use callback methods, and not events, which was different from our MVC approach.
From previous projects, we saw those patterns explode to major Copy+Pasting and CSS/JS duplication/hacking.

So we decided to add another layer of abstraction. 
Every component was simply a Marionette view which defined a strict interface. Each larger "page" view, would render multiple child component views for every component it needed to include.
This way, a button template was defined once, and all CSS classes were encapsulated there (even if those classes were Bootstrappy).
A jQuery datepicker was wrapped, and callbacks were only defined inside the DatePicker view. This DatePicker would trigger specific events to the parent "page" (with the useful "tiggers" hash) allowing for the non-event driven style to be in one specific place.

We took this a step further and extended the Marionette base View object to include a"uiComponents" hash, similar to the "ui" hash. 
This reduced all instantiation, destroying and event binding to a simple declaration on the parent "page" view.

This approach worked great, however, it did add another layer of code and tests. 
It introduced more code to write, albeit easier to maintain in the long run. 
It demanded thinking of component as generic as possible in order to define them correctly.

I am now at the beginning of a new project, and I'm thinking of reusing this design pattern. 
But before I start, I'd love to hear opinions about this approach.

Do you think it takes abstraction too far, especially for simple elements? Do you think it's worth it? 
Do you think it adds unnecessary code?

 

Hyojung Kwon

unread,
Oct 17, 2013, 9:24:34 PM10/17/13
to backbone-...@googlegroups.com
It sounds like your approach is closer to component base rather than template base, if so I think you could consider facebook's react library.
Marionette is a great library to implement view layer on top of Backone. I have been using it in my several projects and helped me to implement web applications successfully and am very satisfied with it. 
However in your case, you want to abstract all granular ui components like button, calendar, form elements and so on. I could easily imagine that you would generate so many files and layer as you mentioned, but using React will make your view structure relatively simpler since it does not require any templates, instead React take advantage of JSX which is sort of xml like syntax in your view javascript files.
I strongly believe that the simple is the best always :)



--
You received this message because you are subscribed to the Google Groups "Backbone.Marionette" group.
To unsubscribe from this group and stop receiving emails from it, send an email to backbone-marion...@googlegroups.com.
To post to this group, send email to backbone-...@googlegroups.com.
Visit this group at http://groups.google.com/group/backbone-marionette.
To view this discussion on the web visit https://groups.google.com/d/msgid/backbone-marionette/195876bb-5d73-4a8e-9148-2564c375ed51%40googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.



--
Hyojung Kwon
(Cell) 82-10-2676-1072

Ken Dickinson

unread,
Mar 19, 2014, 5:54:09 PM3/19/14
to backbone-...@googlegroups.com
I believe this to be a very important topic in terms of the JavaScript MV* universe. One thing I like about Backbone.Marionette is its flexibility. You've certainly demonstrated that by expanding the definition of a "view" to incorporate the concept of a component. I think that components are not discussed heavily enough. All of that said, I have grappled with the best possible way to handle components within the MV* universe and here are some solutions I've come to:

  • Do exactly what you did and use a Marionette ItemView for a component: I can easily envision a scenario wherein you create a view in a Marionette module (which would be within a single file). You could then access that component via App.Components.ComponentName (where Component is the module). Just require the file as needed and its available.
    • This approach has some nice upsides: You are working in a familiar environment and you are able to write all of the event handlers for the component in the view code. Change the look/feel in the template, etc. In general, it's a good way to handle it.
    • There are a couple of downsides: There is a lot of built in functionality within a Marionette (or even a simple backbone) View that you don't really need. That adds unneeded overhead, but might not really be enough overhead to warrant not using it. Also, you have to ensure you have a Marionette app started in order to take this approach.
  • My approach was just to create a jQuery facade pattern for any custom components. In some ways, that is a little less structured than the View approach but has the advantage that I can use my custom components in almost any app because only jQuery is required (and the risk of jQuery not being in an application is a pretty low one - although, I have to admit that some people are moving to Zepto and I haven't tested my jQuery custom components with Zepto yet).
    • The jQuery approach has another advantage: in many cases someone has already done your work for you by creating a custom component. In most cases, those components are customizable in their own right.
    • If there is a downside to this approach I guess it could be the possibility that jQuery may add some extra baggage. I find that pretty doubtful though since Backbone requires jQuery and uses it for much of its 'magic'.
  • There are some component building libraries available:
    • Backbone.Components - I have to admit I've never used this and don't even know if it's supported any more
    • Puppets (https://github.com/Puppets/puppets) - This one is pretty new and seems pretty nice. It's also specifically intended for use with Marionette. My only complaint here is that it may be too new yet (the developer even describes it as 'experimental').
    • Aura (http://aurajs.com/) - Also quite new but getting a nice following (It is developed and supported by Addy Asmani!). I have to say that I really like Aura. If I have a complaint here it is that Aura is almost not opinionated enough. Really, though, opinionated/shminuated - It really all boils down to designing your architecture and sticking to that design (ie being a disciplined developer), does it not?
    • Polymer (http://www.polymer-project.org/) - Polymer is amazing but I think it's too bleeding edge right now.
    • As Ray said, React - It looks good and I'm definitely going to explore it further (I wasn't aware of it - thanks Ray!!!)
  • Finally, it bears mentioning that some MV* libraries have reusable component capability built in (Ember has components, Angular has 'Directives'). What I like about using Backbone.Marionette, though, is that it doesn't lock me in to anything. If I find a better component library, I can swap out. (BTW, I have no experience with Ember development, but I do know it takes plugins too - In fact, it's probable that any of the techniques mentioned above would work with any other MV* library - It's just that I prefer Backbone.Marionette at this point).

Good conversation. If anyone else has something to add, I'm all ears.

pe...@petermumford.com

unread,
Mar 25, 2014, 7:36:31 AM3/25/14
to backbone-...@googlegroups.com
I've been looking for something like this for a while now. I'm currently building a forum for a client and I want to use Backbone and Marionette with Ruby on Rails. But I've never wanted the whole page to be a Marionette view only the forum component its self. This has confused me for a while. 

Ken, you've mentioned a few component based libraries and I really like the look of Aura. I am new to all this front end development so please bare with me. I want to use Backbone with Aura so I can still use the Models, Collections and History. The History is important so the user can navigate to a specific topic or post within the forum as well as going back and forth. The thing is I'm not sure how to achieve this. Do you know of any good resources where I can find the 2 frameworks working together?

I might have got myself a bit confused as Marionette might be a perfect match for what I want? We're developing a google maps section which will also be developed in Backbone and hopefully Marionette but again this will be component based and not the whole page.

Madison Dickson

unread,
Apr 24, 2015, 1:44:36 PM4/24/15
to backbone-...@googlegroups.com
Marionette can be just part of a web page just fine, if you only want to render one view. Would the rest of the page be static then, if you only want one part to be done with Marionette?
If you are already using Backbone for history and navigation, then doing the entire site with Marionette for the Views makes sense, even if 80% of it is static. You'll find that it makes chopping up your UI interactions and handling clicks way more intuitive.

Backbone itself can work from a single view on a page, so Marionette, which is basically just an extension of the Backbone views, can work in the same manner.

I'm still new to Marionette myself, but am really enjoying it so far!
Reply all
Reply to author
Forward
0 new messages