Hi Steve,

Thanks for sharing!

As longtime wicket users we are doing something similar.
We have the notion of a "page context" to which components can contribute data (it's a simple map<String, Object>) by implementing an interface (PageContextContributor).
A component can then either:
- add an InlineContextLabel, which will replace expressions in it's body using the page context, or - add an InlineContextMarkupContainer, which can serve as a parent to wicket:message tags, so they can resolve properties in the page context

The reason we have started using this in more recent projects is that we didn't like the split you get once you have pages (or components) which have localized html files, but also contain some "dynamic" content: labels with property replacement. Before using our above solution, we would have some of the content in properties files, and some in the localized html files. Now we can have a lot more of the localized stuff directly in the html files.

I'll have a look at your code.

Met vriendelijke groet,
Kind regards,

Bas Gooren

schreef Steve op 21-11-2013 12:05:
This will probably horrify some of the wicket dev team.  It's probably
not the 'wicket way'.  But I've been using wicket for years and there's
plenty of thing you can do in many different ways but a few things that
you just can't.

An incidental but very useful part of this package in a Renderer class.
It's an extension of wicket's ComponentRenderer that allows you to
Render components without having to create a wicket application.  If you
do happen to be inside a wicket application when you invoke it no
problem.  But with the wicket version you have no choice.  So for a
quick and dirty HTML output it lets you go with 2 lines of code:

Renderer.init();
String html = Renderer.renderComponent(myPanel).toString();

The main part of the package is an integration of JUEL with wicket
allowing you to put Java Expression Language into your markup which will
be evaluated just before the wicket rendering cycle.  It might seem odd
but I've wished this was part of wicket for years.  There's many times
when I just want to populate a html element with a bean property and it
gets a bit tedious having to add it in both markup and code.  It also
makes dynamic markup generation a lot easier given that your generator
only needs to spit out HTML for many purposes and doesn't need to
generate java code as well.

The wicket version would be something like this:

markup:
<span wicket:id="label1" color="red"></span> <span
wicket:id="label2"></span>

code:
add(new Label("label1", bean.getFirstName())
.add(AttributeModifier.replace("color", new Model("green") {
     public String getObject() {
         bean.getColor();
     }
}));
add(new Label("label2", bean.getLastName());

The EL version would be simply:more

<span color="bean.color">${bean.firstName}</span>
<span>${bean.lastName}</span>

No code needed at all if 'bean' is a property of the Component.
Otherwise you can just add a single line:
setELBaseObject(bean);

then the above html becomes even simpler:
<span color="color">${firstName}</span> <span>${lastName}</span>

All the magic of wicket is retained.  But with a much neater way of
adding simple values to markup.

The code is model aware.  If any part of an expression evaluates to a
wicket model it will be unwrapped before the rest of the expression is
evaluated.  So all the model magic is also retained and models can be
used to achieve anything particularly fancy needed for an evaluation.

Currently the code is split into two behaviours.  The first part enables
modifiable markup.  If you want a simple way to interfere with markup
before wicket gets to it you can use this behaviour on it's own by
overriding a single method: String modifyMarkup(String).  The second
part is the EL implementation (which uses the JUEL library).  Both are
implemented using the behaviour pattern because there's no common parent
class to inject this behaviour into the Component class heirarchy.
Currently there's implementations for Panel, ListView and Page but
looking at those an example should give you an idea how to add the
behaviour to other component types.

Be warned the code is very fresh so is likely got a few bugs and I have
fairly hefty TODO list.  But I intend using it for a couple of projects
I'm working on so it should be getting plenty of developer love in the
near future.  I'm the first to admit it's a bit hacky in the way it
hooks into the wicket lifecycle.  Wicket really doesn't make it easy to
intercept markup.  With luck the dev team won't hate this idea too much
and might provide some neater hooks in future versions of the API.

You can find it here: https://bitbucket.org/shadders/wicket-el



---------------------------------------------------------------------
To unsubscribe, e-mail: users-unsubscr...@wicket.apache.org
For additional commands, e-mail: users-h...@wicket.apache.org


Reply via email to