2

I'm implementing some search filters. A <p:commandLink> is displayed beside each search component (<p:inputText>, <p:selectOneMenu> etc).

<p:inputText id="text" value="#{bean.text}" required="true"/>

<h:panelGroup id="panelGroup">
    <p:commandLink process="@this text" update="panelGroup text" actionListener="#{bean.action}" rendered="#{empty param['form:text']}">
        <h:outputText styleClass="ui-icon ui-icon-search"/>
    </p:commandLink>

    <p:commandLink process="@this" update="panelGroup text" actionListener="#{bean.resetAction}" rendered="#{not empty param['form:text']}">
        <h:outputText styleClass="ui-icon ui-icon-trash"/>
        <p:resetInput target="text"/>
    </p:commandLink>
</h:panelGroup>

When the first <p:commandLink> (the one with the search icon) is clicked and the given <p:inputText> is not empty, the link is expected to disappear and another link (the one with the trash icon) is expected to be rendered (and vice versa).

This happens but the action listener as indicated by the first link (actionListener="#{bean.action}") is not invoked because the link is rendered based on the value of <p:inputText>. rendered="#{empty param['form:text']}" is responsible for preventing the listener from being invoked.

Also when the link with the trash icon appears, it resets the input component, if it is clicked but it does not disappear. it disappears only when it is clicked once again (and then the search appears).


How to handle this situation correctly? If no validation/conversion is violated and the search link is clicked then, the link should disappear and the trash link should be rendered.

On the contrary, when the trash link appears and if it is clicked, it should reset the <p:inputText> and then disappear so that the search link can be rendered.

Tiny
  • 27,221
  • 105
  • 339
  • 599

1 Answers1

2

You actually want to toggle the rendering only after the action is invoked. The rendered attribute is namely also obeyed during apply request values phase, when the action event is about to be queued. If it evaluates false, then the action event won't be queued and therefore the action won't be invoked during invoke application phase.

Better just check the model value directly. The action is queued before the model value is set. And, this should also work better when there's conversion/validation on the model value.

<p:inputText ... value="#{bean.text}" />
<p:commandLink ... rendered="#{empty bean.text}" />
<p:commandLink ... rendered="#{not empty bean.text}" />
BalusC
  • 1,082,665
  • 372
  • 3,610
  • 3,555