tags:

views:

115

answers:

3

I want to dynamically pick a facelet to render some item in my data list. The first try would be:

<ui:repeat value="#{panels}" var="panel">
  <ui:include src="#{panel.facelet}">
</ui:repeat>

But it won't work since src of ui:include is evaluated too early. The facelet information is truly dynamic, so I cannot use c:forEach (not really recommended to mix with facelets either). I guess it all boils down to finding a component based ui:include alternative.

Is there such thing or I need to write my own?

+4  A: 

c:forEach will solve it, why can't you use it?

Interesting article regarding that issue: http://www.ilikespam.com/blog/c:foreach-vs-ui:repeat-in-facelets

MrOhad
Thanks but c:forEach is evaluated once, when the view is built. In my case what's under #{panels} can change while user interacts with the page.
mrembisz
A: 

I remember trying to do something similar using a custom tag and FaceletHandler etc. In the end all the little rendering-time issues made it not worth the effort. Mind you I was (and still am :-(...) using facelets for jsf 1.1, so not sure if this is better in the later versions.

How dynamic / how many different facelets do you have to deal with? The reason I ask is that you could (to borrow a term from the compiler wizards) unroll your loop. Instead of

<ui:repeat value="#{panels}" var="panel">
  <ui:include src="#{panel.facelet}">
</ui:repeat>

You could do

<custom:panelOneFacelet rendered="#{hasPanel1}" />
<custom:panelTwoFacelet rendered="#{hasPanel2}" />
<!-- etc... -->

And in your facelet, you would have something like :

<c:if test="#rendered" >
    <!-- EVERYTHING IN THE FACELET HERE!!!-->
</c:if>

This sort of low-tech approach is fine for a small controlled set, but if you have a very large and varying set of facelets this may not work.

Might I ask why, b/c sometimes with an understanding of the high-level, SO gurus may suggest much simpler ideas for accomplishing the same goal

Java Drinker
Basically we render a business form which is provided to us as a tree of data fields. What you describe here was our first try but it turned out to be very resource consuming since in each node we had a complete set of possible rendering options. We ended up implementing our own include tag + component which works fine but is a real pain to maintain due to complexity and jsf internals. We did this nearly 3 years ago and now plan on moving to jsf2. I was hoping some out-of-the-box alternative appeared by this time.
mrembisz
Hmmm.. not sure I understand... so you have like Library { location, name, List<Book> books} where Book { name, isbn, Author} where Author {name, age, ..} Something like that? And you would like to get that kind of structure to generate a tree of forms fields?... I must have this wrong, eh?.. This seems much too complex for me, I would break all that down to different forms and beans etc...
Java Drinker
You've got it right, this is exactly what we have and we don't know the record structure until runtime. As I said we have a working but quite complex solution. I would like to investigate the possibility of dropping our custom jsf include logic.
mrembisz
+1  A: 

you have to write your own tag...nothing else you can do as far asI checked