views:

1020

answers:

7

I am building an application where most of the HTML is built using javascript. The DOM structure is built using some JSON data structures that are sent from the server, and then the client-side code builds a UI for that data.

My current approach is to walk the JSON data structures, and call script.aculo.us's Builder.node method to build the DOM structure, and then append it to some element that is actually in the HTML sent from the server. Along the way, I am registering event listeners to the various elements that need them. This allows for a good amount of flexibility, and allows for a very dynamic interface.

However, I feel that it is not very sustainable, since the view logic (ie, the DOM structure) is so tightly coupled to the code that walks the data, and the event handlers, and the data that is kept in memory to maintain the state, and is able to communicate those changes back to the server.

Are there any template-like solutions that will allow me to divorce the DOM structure from the code that drives the app? Currently, my only library dependencies are prototype.js and script.aculo.us, so I would like to avoid introducing any large libraries, but any suggestions are welcome.

Thanks!

EDIT: For some reason, What good template language is supported in Javascript? didn't show up in the little search results when I was typing this question. It does, however, show up in the "Related" sidebar here.

I will read through some of the suggestions there, and if I find a solution, I will close this question. Otherwise, I will clarify this question with reasons why those solutions won't work for me.

+1  A: 

there are several 'template' plugins for jQuery:

There are some XSLT extras that do all transform in the client, but i don't think XSL is 'designer friendly' enough

Javier
+6  A: 

There are some template solutions out there, but they aren't doing much more than you're doing already. jQuery has been doing some work along these lines, and some jQuery plugins have emerged as solutions. Prototype.js and others have solutions as well.

Some options include:

In general, Ext js has some pretty wild and tricked out stuff, including some templates, but you'd be adding yet another library. So many libraries are getting tossed around these days, and it's often so much simpler to implement a light and simple custom solution. Try creating some DOM objects on your own. If you've got JSON data, parse it into memory and run it through a function. It's actually a blast, and a lot of people are doing it.

Sidenote: What you're doing may be quite sustainable and maintainable. Keep in mind that when you send a page of HTML, the browser is putting a DOM structure into memory in roughly the same way that your javascript does. I don't particularly recommend any of these solutions. It sounds like you've made a nice little system for your specific needs, and I'd generally say that refining your design will be at least as valuable as moving to somebody else's pattern, with the added benefit of being able to create some of your own dependencies.

Sidenote: It's generally not advisable to generate the entire DOM on the client, at least not for many markets. Sometimes it's an A-OK solution, as it may be in your case, but it's worth a note of caution to the audience at large that this style of development is not always the best road to travel.

keparo
Perhaps I should have said 'maintainable' rather than 'sustainable'. I'm not so worried about performance (though making a zillion AJAX requests for jsp pages is unacceptable). I'm mostly worried about wanting to change the structure of a section in the future.
pkaeding
Ah. -sounds like you want a flexible way to change the construction of your DOM objects. It may be that Builder.node is handling so much of the construction for you that you have less control than you'd like. Try constructing objects yourself. From JSON, it should be easy, and you'll be in control.
keparo
A: 

If I'm understanding the question, you would like to be able to build a GUI dynamically, but based upon predefined HTML templates? I know that I have often felt strange about building DOMs using JS when there's a perfectly good language (HTML) for doing the same.

You could use XMLHttpRequests for boilerplate blocks of XHTML, then modify those blocks as needed in your code. When I have done it that way, I find it gives a more satisfying separation of logic and presentation.

Joel Anair
A: 

ExtJS has an excellent templating syntax: link text

harley.333
+1  A: 

Your template could be encapsulated in a widget. Prototype has a means to create add-ons, however I am most familiar with how to do this in jQuery. I tried prototype first, but later realized jQuery has everyting prototype has and more. It also has more add-ons / widgets / plug-ins created by the user community.

Builder is just an add-on to prototype. however, building html DOM elements in jQuery is part of the core functionality.

http://docs.jquery.com/Core/jQuery#html combined with: http://docs.jquery.com/Manipulation/append#content

here is a sample of building some html and adding it to a jQuery element selection.

$(document.body).append($('<div id="sub-menu-holder" style="position:absolute;top:0;left:0;border:0px none;"></div>'));

You can also get data structures from ajax calls and use that to create entities, or you can just return html from the ajax call and append it directly to the DOM in the appropriate location.

http://docs.jquery.com/Ajax/load#urldatacallback

Here is the sample from the jquery load function documentation.

$(document).ready(function(){ $("#links").load("/Main_Page #jq-p-Getting-Started li"); });

That's it. If your ajax call returns all the html to be inserted, and you know the element id where it goes that is all you need. Now all you need is to detemine how to create the html on the server side. Without knowing specific details on what you are building that is hard to answer. But your templating engine on the server side doesn't need to know much about where the generated html will be placed.

Michael
A: 

QueryTemplates allows you to fully separate markup from logic. It uses DOM and CSS selectors to achieve that. It has light version for JavaScript (as jQuery plugin) and standard version which can generated native JS code (no library needed to execute it). You need PHP to generate the template with standard version (CLI version is fine). Library is based on phpQuery, a jQuery port to PHP.

You can see demo of JavaScript version. Using standard version you can get quite client-side experience inside PHP - there are DOM events, JSON support, even AJAX with JSONP.

Tobiasz Cudnik
A: 

If you are using Script# you may want to consider SharpTemplate, a strongly typed, super efficient HTML templating engine.

Shiva