如何在单个dataTable中显示不同对象类型的不同值?

时间:2011-06-11 21:08:47

标签: java jsf facelets java-ee-6

我有一个对象(Ticket),它有一个其他对象列表(Message)。消息是抽象的,并且有几个子类 - 如EditMessage,CreationMessage等。因此Ticket对象包含混合的消息,并按创建时间排序。

现在我想在Facelets页面中显示所有这些消息,我需要输出特定于该消息类型的字段值:即,EditMessage中的editedField,CreationMessage中的userName,...

最明显的方式似乎是使用h:dataTable:

<h:dataTable value="#{ticketController.ticket.messages}" var="msg" >
    // determine type of message, cast, and use <c:if> to output needed values
</h:dataTable>

问题是Facelets表达式语言没有“instanceof”和强制转换。据我所知,这可以通过对托管bean进行一些丑陋的往返解决,在标准Java中确定消息类型,返回所需类型的消息,......等等来解决。

有没有更好,更易理解和简洁的方法呢?

<小时/> 解决方案

我的主要问题是&lt; c:if&gt;标签。事实证明它是一个JSTL标记,因此它具有略微不同的渲染生命周期。而不是它,我现在使用&lt; h:panelGroup&gt;及其“渲染”属性。

一些代码:

<h:dataTable value="#{ticketController.ticket.messages}" var="msg" >
    <h:column>
        <h:panelGroup rendered="#{msg.class.name == 'org.rogach.tsnt.TextMessage'}" >
            <h:outputText value="msg.text" />
        </h:panelGroup>
        <h:outputText value="#{msg.creationTime}" />
    </h:column>
</h:dataTable>

不需要演员表。

1 个答案:

答案 0 :(得分:3)

而不是 instanceof ,比较对象类的名称 说: <c:if test="${xxx.class.name == 'CreationMessage'}">或c:选择
你不需要任何EL演员。如果对象没有你指定的某个属性,它会给出一个例外,如果它确实没有。