Ractive.js – Tutorial for applying templating and viewmodel pattern

Decouple view and model layer with Ractive.js

I recently needed a javascript template library for some projects in which I am involved, so I gave a look into web for some suggestions.

I must say Ractive.js impressed me for the ease of use as well as the small learning curve; furthermore is not invasive and can be used with other libraries.

With Ractive.js is possible to apply the ViewModel pattern and apply the separation of view and model layer throught binding; it is also possible to build decorators, components and other stuff that incapsulate the logic inside a reusable script code.

In order to show what are the main differences between the code with and without RactiveJS, I’ll show a simple example:

An html page that contains

two input text
a submit button
a warning message on empty value

The validation rules are simple:
the submit message is disabled until the two input are empty


Code without Ractive.js

This is the html body section, nothing to say about it 🙂

The logic script code shown below basically check if name and surname values are empty, and if not, the submit button enable itself; there is also a message for each input that warn the user to enter some value.

If your take a look to the comments //, you will agree that there are pieces of code that are coupled with the view layer, because it is needed to take value from elements by their id and either because of the call to jQuery UI functions (i.e. node.button() ).

In a typical MVVM pattern situation, this doesn’t happen, because viewmodel must NOT know of the view part.

This is where Ractive.js does the matter.

Code with Ractive.js

Take a look to the following code:

You will notice some expressions inside braces {{ }}; looking with a more accurate eye, some id element’s attributes disappeared, more likely because they are not referenced anymore.

{{name}} and {{surname}} are the binded name (or keypath) that belongs from the viewmodel object, that is the effective datacontext of this view.
An inverted section begins with a caret (hat) and ends with a slash. So {{^name}} can be traslated in (if not name then), that is all the code within the bracets will be displayed ONLY if name is empty.

Finally, there is a odd attribute named “decorator” inside the submit button; we’ll take care ahead this article.

The logic section is pretty interesting because totally avoids any reference to the view part, instead it only takes care of the model and pure logic part (if any).

Notice the ractive observe directive watch for any change of the value, and not for the change event of the node (in which  you should use proxy events like on-change).

All logic that involve the view components (like showing or disabling elements) is relied only on the html and not the model so the two layers are good decoupled.

Now you are wondering where are the calls to jQuery UI buttons; for this purpose I created a dedicated decorator to deal with jQuery UI components that is reusable for most of my future web applications.

The code for jQuery button decorator is the following:

Basically, once the button element is rendered this decorator call button() to its attached node.

Internally, a MutationObserver check for any change in the state of the node, in this case properly filtered with ‘disabled’ attribute, and then call for button(‘enable|disable’).

Final considerations

Learning fundamentals of Ractive.js can be more easier with the  interactive tutorial that provides to user a valid base to begin. Separation of layer concepts, data binding and build of components make it sometimes fun and challenging. Try it!

Be the first to comment

Leave a Reply

Your email address will not be published.

To create code blocks or other preformatted text, indent by four spaces:

    This will be displayed in a monospaced font. The first four 
    spaces will be stripped off, but all other whitespace
    will be preserved.
    Markdown is turned off in code blocks:
     [This is not a link](http://example.com)

To create not a block, but an inline code span, use backticks:

Here is some inline `code`.

For more help see http://daringfireball.net/projects/markdown/syntax