【问题标题】:JSF2 composite component - condition on method attribute existencJSF 2 复合组件 - 以方法属性存在为条件
【发布时间】:2011-10-09 10:12:01
【问题描述】:

我有一个简单的复合组件,带有一个可选的 ajax 侦听器,使用 Richfaces a4j:ajax 组件实现。

这是接口定义:

<!-- INTERFACE -->
<composite:interface name="inplaceInput">
    <composite:attribute name="value" required="true" />
    <composite:attribute name="render" default="@this" />
    <composite:attribute name="ajaxListener" method-signature="void actionListener(javax.faces.event.AjaxBehaviorEvent)" />
</composite:interface>

以下代码使用两个具有相反渲染条件的重复块可以正常工作:

<composite:implementation>
    <rich:inplaceInput value="#{cc.attrs.value}" rendered="#{!empty cc.attrs.ajaxListener}">
        <a4j:ajax event="change" render="#{cc.attrs.render}" execute="@this" listener="#{cc.attrs.ajaxListener}" />
    </rich:inplaceInput>
    <rich:inplaceInput value="#{cc.attrs.value}" rendered="#{empty cc.attrs.ajaxListener}">
        <a4j:ajax event="change" render="#{cc.attrs.render}" execute="@this" />
    </rich:inplaceInput>
</composite:implementation>

但我想避免重复,因为我的组件要复杂得多......

在 a4j:ajax 上使用渲染条件是我的第一个想法:

<rich:inplaceInput value="#{cc.attrs.value}">
    <a4j:ajax event="change" render="#{cc.attrs.render}" execute="@this" listener="#{cc.attrs.ajaxListener}" rendered="#{!empty cc.attrs.ajaxListener}"  />
    <a4j:ajax event="change" render="#{cc.attrs.render}" execute="@this" rendered="#{empty cc.attrs.ajaxListener}" />
</rich:inplaceInput>

但它不起作用,而且错误很模糊:

javax.faces.FacesException: Unable to resolve composite component from using page using EL expression '#{cc.attrs.ajaxListener}'
at com.sun.faces.facelets.tag.TagAttributeImpl$AttributeLookupMethodExpression.invoke(TagAttributeImpl.java:444)
at org.ajax4jsf.component.behavior.MethodExpressionAjaxBehaviorListener.processAjaxBehavior(MethodExpressionAjaxBehaviorListener.java:73)

我尝试使用 c:if 处理程序,因为树不需要同时包含两个组件:

<rich:inplaceInput value="#{cc.attrs.value}">
    <c:if test="#{!empty cc.attrs.ajaxListener}">
        <a4j:ajax event="change" render="#{cc.attrs.render}" execute="@this" listener="#{cc.attrs.ajaxListener}" />
    </c:if>
    <c:if test="#{empty cc.attrs.ajaxListener}">
        <a4j:ajax event="change" render="#{cc.attrs.render}" execute="@this" />
    </c:if>
</rich:inplaceInput>

然后又出现了一个错误(使用 ajaxListener="#{itemList.updateValue}"):

javax.el.PropertyNotFoundException: /pages/itemList.xhtml @71,81 ajaxListener="#{itemList.updateValue}": Property 'updateValue' not found on type com...ItemListManager

如果属性是一个返回值的 EL,我可以测试一个默认值。我还可以添加一个布尔属性来判断是否设置了侦听器...或者在 componentType bean 上添加一个默认方法什么都不做...但这并不漂亮...

如何在不访问属性值或方法绑定的情况下测试属性是否已设置?

提前感谢您的任何想法,

Rgds,

调频

【问题讨论】:

    标签: jsf-2 composite-component rendered-attribute


    【解决方案1】:

    您可以使用UIComponent 类中的cc.getValueExpression() 来检查是否在复合组件的使用页面中定义了值表达式,如下所示:

    <c:if test="#{!empty cc.getValueExpression('ajaxListener')}">     
      <a4j:ajax event="change" render="#{cc.attrs.render}" execute="@this" listener="#{cc.attrs.ajaxListener}" />     
    </c:if> 
    

    【讨论】:

    • 使用这个有什么特殊要求吗?首先,我的 EL 解析器不喜欢 ()。它适用于 [],但在访问显示“UINaming Container 没有属性 getValueExpression”的页面时出现错误。
    • Louise:您需要使用 EL-api 2.2 版才能使用此代码。
    猜你喜欢
    • 2012-10-21
    • 1970-01-01
    • 2011-07-24
    • 2013-11-10
    • 1970-01-01
    • 2011-06-02
    • 2012-07-07
    • 2012-08-25
    • 2012-01-09
    相关资源
    最近更新 更多