小编典典

将JSF标签与JSTL标签混合会产生奇怪的结果

java

我有这段代码:

 <c:if test="#{utils.getCounterOfCharOccurence(hideTypes, ';') != 0}">
   <ui:repeat value="#{document.instanceList}" var="instance">
    <c:set var="columnRendered" value="true"></c:set>
    <c:forEach items="${hideTypes.split(';')}"
               var="hideType">
     <h:outputText value="#{hideType eq instance.documentInstanceType.mimeType}"/>
     <c:if test="#{hideType eq instance.documentInstanceType.mimeType}">
      <c:set var="columnRendered" value="false"></c:set>
      <h:outputText value="#{columnRendered}|"/>
     </c:if>
    </c:forEach>
    <a:outputPanel rendered="#{columnRendered == 'true'}">
     <up:mimeTypeIcon type="#{instance.documentInstanceType.mimeType}"
                      icon="#{instance.documentInstanceType.iconPath}"
                      key="#{instance.instanceKey}" referenced="false"/>
    </a:outputPanel>
   </ui:repeat>

  </c:if>

如您所见,我仅在columnRendered为true时才渲染该outputPanel。

好吧,在某些情况下(仅用于测试以批准其应做的事情):

<h:outputText value="#{hideType eq instance.documentInstanceType.mimeType}"/>

为true,因此应在c:if中输入,并将columnRendered切换为false。但是事实并非如此,因此columnRendered永远是正确的…

你知道为什么吗?


阅读 224

收藏
2020-09-26

共1个答案

小编典典

JSF和JSTL不会像您期望的那样同步运行。JSTL在视图的构建期间(要填充JSF组件树)运行,而JSF在视图的组件树的呈现期间(要生成HTML输出)运行。您可以将其可视化如下:JSTL首先从上到下运行,然后将结果交给JSF,后者又从上到下运行。

在您的特定情况下,该对象instance永远不会出现在JSTL中。

代替c:forEach,应该使用ui:repeat,而不是c:if使用JSF组件的rendered属性。我想重写代码,但是的用法hideTypes很乱。而是将其转换List<String>为模型中的,使用纯JSF会更加容易。这是一个假设hideTypes为的启动示例List<String>

<h:panelGroup rendered="#{not empty hideTypes}">
    <ui:repeat value="#{document.instanceList}" var="instance">
        <a:outputPanel rendered="#{!hideTypes.contains(instance.documentInstanceType.mimeType)}">
            <up:mimeTypeIcon type="#{instance.documentInstanceType.mimeType}"
                icon="#{instance.documentInstanceType.iconPath}"
                key="#{instance.instanceKey}" referenced="false"/>
        </a:outputPanel>
     </ui:repeat>
<h:panelGroup>
2020-09-26