I am interested in creating a dynamic component in JSF. By that I mean a component that looks and acts differently dependent on the variables it is passed.
Let's take an easy example that actually works. A composite component (facelet) that hides/shows different parts of itself dependent on the data. In this case, it takes an attribute named "myBean", which you may imagine having a "value" field and "type" field. The "type" field determines what component should be rendered.
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:jsp="http://java.sun.com/JSP/Page"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:c="http://java.sun.com/jsp/jstl/core"
xmlns:cc="http://java.sun.com/jsf/composite">
<cc:interface>
<cc:attribute name="myBean" />
</cc:interface>
<cc:implementation>
<!-- Small input field if type is "shorttext" -->
<h:inputText value="#{myBean.value}" rendered="#{myBean.type == 'shorttext'}" />
<!-- Text area input field if type is "longtext" -->
<h:inputTextArea value="#{myBean.value}" rendered="#{myBean.type == 'longtext'}" />
</cc:implementation>
</html>
While this works, it quickly becomes unwieldy. If I have twenty different types, I have them all specified in the same document and that clearly violates good design.
Instead, I would like to be able to replace the implementation with something like:
<ui:include value="#{myBean.type}"/>
Which I understand is not possible, since ui:include
occurs when building the component tree, and the the component is processed during the rendering phase.
Yet this must be a common problem. What is the best approach to achieve dynamic components? I am using JSF 2.0, if that makes a difference.