有条件地设置ui:param

Fra*_*sco 9 facelets primefaces jsf-2

我想根据bean值设置一个ui:param,我想用c:if是个好主意.所以我在我的页面中输入以下代码:

<ui:composition xmlns="http://www.w3.org/1999/xhtml"
    xmlns:ui="http://java.sun.com/jsf/facelets"
    xmlns:h="http://java.sun.com/jsf/html"
    xmlns:f="http://java.sun.com/jsf/core"
    xmlns:c="http://java.sun.com/jsp/jstl/core"
    xmlns:wai="http://www.id.ethz.ch/wai/jsf"
    template="/view/listView.xhtml">

        <c:if test="#{subscriptionListController.model.listViewName eq 'mySubscriptions'}">
         <ui:param name="title" value="#{msg.subscriptionTitleMySubscriptions}"/>
        </c:if>
        <c:if test="#{subscriptionListController.model.listViewName eq 'paidSubscriptions'}">
         <ui:param name="title" value="#{msg.subscriptionTitlePaidSubscriptions}"/>
        </c:if>
        <c:if test="#{subscriptionListController.model.listViewName eq 'allSubscriptions'}">
         <ui:param name="title" value="#{msg.subscriptionTitleAllSubscriptions}"/>
        </c:if>
        ....
Run Code Online (Sandbox Code Playgroud)

但参数未设置...

如果我打印出来的值,#{subscriptionListController.model.listViewName eq 'mySubscriptions'}我会在相应的情况下得到真值,而在其他两种情况下则为假.

一开始我只有两种可能性并用三元运算符解决了它:

<ui:param name="title" value="#{subscriptionListController.model.listViewName eq 'mySubscriptions' ? msg.subscriptionTitleMySubscriptions : msg.subscriptionTitlePaidSubscriptions}"/>
Run Code Online (Sandbox Code Playgroud)

它起作用了.但现在我有更多的可能性......

我究竟做错了什么?

Bal*_*usC 11

如图所示<ui:composition template>,此页面代表模板客户端.

任何<ui:param>外部都<ui:define>适用于主模板(您在template属性中声明的文件),并在模板客户端本身内被忽略.如果您打算在模板客户端内部准备变量,则应将其置于<ui:param>内部<ui:define>.

但还有另一件事:最初的目的<ui:param>是将变量传递给引用的文件<ui:composition template>,<ui:decorate template>或者<ui:include src>不在当前facelet上下文中准备/设置变量.对于在当前EL上下文中准备/设置变量的唯一功能要求,您最好使用JSTL <c:set>来完成工作.您可以使用<ui:param>此功能,但这不是它的原始意图,并且在较旧的MyFaces版本中不起作用.

因此,所以:

<ui:define>
    <c:if test="#{subscriptionListController.model.listViewName eq 'mySubscriptions'}">
        <c:set var="title" value="#{msg.subscriptionTitleMySubscriptions}"/>
    </c:if>
    <c:if test="#{subscriptionListController.model.listViewName eq 'paidSubscriptions'}">
        <c:set var="title" value="#{msg.subscriptionTitlePaidSubscriptions}"/>
    </c:if>
    <c:if test="#{subscriptionListController.model.listViewName eq 'allSubscriptions'}">
        <c:set var="title" value="#{msg.subscriptionTitleAllSubscriptions}"/>
    </c:if>
    ...
</ui:define>
Run Code Online (Sandbox Code Playgroud)

具体问题无关,您可以按如下方式对其进行优化,而不需要一个<c:if>只能在每个订阅类型中增长的不可维护的组:

<ui:define>
    <c:set var="subscriptionTitleKey" value="subscriptionTitle.#{subscriptionListController.model.listViewName}">
    <c:set var="title" value="#{msg[subscriptionTitleKey]}"/>
    ...
</ui:define>
Run Code Online (Sandbox Code Playgroud)

用那些钥匙

subscriptionTitle.mySubscriptions = Title for my subscriptions
subscriptionTitle.paidSubscriptions = Title for paid subscriptions
subscriptionTitle.allSubscriptions = Title for all subscriptions
Run Code Online (Sandbox Code Playgroud)

  • "......反过来在技术上是错误的,只在Mojarra工作,但不在MyFaces工作......"这不是真的.相反,它恰恰相反.这是一个looooonnngggg故事,但我在[MYFACES-3169](https://issues.apache.org/jira/browse/MYFACES-3169)中写了原因.最近在[MYFACES-3810](https://issues.apache.org/jira/browse/MYFACES-3810)中,它在2.2.x分支中添加了一个标志以启用旧行为.ui:param仅在ui的直接子项中有效:include,ui:decorate或ui:composition但是params在目标模板的上下文中可用.在c里面使用它们:如果是个坏主意. (3认同)