Categorized | News, OOP

Implementing an Output Renderer Strategy

Posted on 29 September 2005 by Demian Turner

An interesting design problem became apparent when a
number of folks from the seagull ML recently complained about the lack
of support for web clients other than standard browsers. Because the code
enforces reasonable segregation between the domain modelling and the
html views, I always presumed it would be trivial to implement, ie, an
xml renderer instead of the current Flexy to handle WML output.
Two problems needed to be solved:

  1. the Flexy renderer was hard-coded in the final stage of a validate/process/display workflow
  2. worse, a number of post-processing tasks, mainly assembling of blocks and building of main navigation were also hard-coded

In short, the process was quite tied to producing HTML-only output, clearly n
blocks and involved navigation were unsuitable for PDA output.

I
identified two main refactorings necessary to decouple the view
production from the output type and specific renderer used, thereby
opening the door to running customised post-process tasks based on the current
rendering strategy.

To
allow an arbitrary renderer to be specified at runtime I chose to
compose the View object with a OutputRendererStrategy. This means
if you’re happy with Flexy you can use the standard renderer supplied
with the package, and if you can’t bear the thought of working without
Smarty, it’d be a piece of cake to write a SmartyOutputRenderStrategy
following the Flexy example. The code would look something like
this:

    //  build view
$view = new SGL_HtmlView($output, new SGL_HtmlFlexyRendererStrategy());
echo $view->render();

where the $output object is just a php data structure free of any
presentation information. The next problem was more interesting,
how does producing output for portable devices change the appliation
requirements. The basic data structure sent to the view is
similar, but the following main differences are evident:

  • any paginated lists sent to the template needed to be a lot shorter, with simpler paging
  • any superfluous info like that found in left/right column blocks had to go
  • navigation had to be dramatically simplified

Using the View type but switching implementation as runtime made it
very easy to achieve this, where WmlView implements specialised
minimalist post processing tasks, and uses an xlst renderer to output
WML. The code would look like this:

    //  build view
$view = new SGL_WmlView($output, new SGL_XmlRendererStrategy());
echo $view->render();

The code
is currently only in svn but will make it out in the 0.5.1 devel
release planned shortly. The following UML summarises the idea:

Bookmark and Share

2 Comments For This Post

  1. Luke S. K. Says:

    It’s nice to see the abstraction, as I have a feeling renderer systems like these will become more prevailaint. In the design of a game engine, the rederer is usually an abstract factory to provide portability. Since HTML is just one form, albiet the most popular, of representing data on the web, it only makes sense to abstract view generation in this fashion. Nice design, looks good. 😉

  2. Michael Heuberger Says:

    Nice Demian, you used the strategy design pattern. I am very happy about different rendering strategies. So I can make seagull websites compatible for mobile devices with a minimum of effort.

    great job!

    Mick

Leave a Reply

Categories

Books

Demian Turner's currently-reading book recommendations, reviews, favorite quotes, book clubs, book trivia, book lists

Facebook