如何通过ajax在p:tab下动态地show/hide组件?

How to dynamically show/hide components under p:tab via ajax?

请原谅我,我什至不确定我的问题是否正确陈述。我试图弄清楚 p:tab 和 h:panelGroup 之间的关系。我对JSF的了解很浅。我有以下代码。

<p:tabView id="view">
    <p:tab id="A">
        ...
        <p:ajax event="change" update="C,D" listener="#{bean.captureValue}"/>
    </p:tab>
    <p:tab id="B" titleStyleClass="x">
        <h:panelGroup id="C">
            <h:panelGroup rendered="#{bean.checkValue eq 'Yes'}"/>
                <f:facet name="title"><table>...</table></f:facet>
                <div>....</div>
            </h:panelGroup>
        </h:panelGroup>
        <h:panelGroup id="D">
            <h:panelGroup rendered="#{bean.checkValue eq 'No'}"/>
                <f:facet name="title"><table>.....</table></f:facet>
                <div>....</div>
            </h:panelGroup>
        </h:panelGroup>
    </p:tab>
</p:tabView>

因此在组件 id="A" 中,用户从下拉菜单中选择一个值,bean 捕获它并动态显示或隐藏组件 id="C" 或 "D" 基于价值。

第一次尝试,我没有任何 h:panelGroup 标签。我直接从 p:tab 组件使用渲染属性,但是我意识到除非我刷新整个页面,否则 bean.checkValue 不会知道捕获的最新值。通过阅读这个论坛中的许多文章,我意识到我必须用 h:panelGroup 包装它,这反过来通过根据从中选择的值显示 h:panelGroup "C" 或 "D" 来工作p:tab 标签 ID="A".

但是 f:facet 标签的内容不再可见。它有 html table 标签,其中包含带有静态值的 h:outputText 和 p:graphicImage。不知道为什么,希望有人能解开这个谜。

更新:

感谢亚瑟。在他的帮助下,我能够解决这个问题。我在此处粘贴执行预期输出的代码。

<p:tabView id="view">
    <p:tab id="A">
        ...
        <p:ajax event="change" update="view" listener="#{bean.captureValue}"/>
    </p:tab>
    <p:tab id="B" titleStyleClass="x">             
          <f:facet name="title">
              <ui:fragment rendered="#{bean.checkValue eq 'Yes'}"/>
                 <table>...</table>
              </ui:fragment>
          </f:facet>
          <ui:fragment rendered="#{bean.checkValue eq 'Yes'}"/>
              <div>...</div>
          </ui:fragment>


           <f:facet name="title">
              <ui:fragment rendered="#{bean.checkValue eq 'No'}"/>
                 <table>...</table>
              </ui:fragment>
          </f:facet>
          <ui:fragment rendered="#{bean.checkValue eq 'No'}"/>
              <div>...</div>
          </ui:fragment>            
    </p:tab>
</p:tabView>

构面表示容器组件中的命名部分。在这两种情况下,您的方面的容器都是 <h:panelGroup> 并且此组件未定义您可以使用的任何方面。由于您没有在示例代码中为该方面提供任何名称(这是强制性的),我只假设您可能想为选项卡使用标题方面,因为 <p:tab> 组件定义名为 [=26 的方面=].那么它应该看起来像

<p:tab id="B">
        <f:facet name="title" >
            <h:outputText value="Test1" rendered="#{bean.checkValue}"/>
            <h:outputText value="Test2" rendered="#{!bean.checkValue}"/>
        </f:facet>
</p:tab>

,所以你在 facet 值内实现渲染逻辑(你决定显示哪个标题。这个逻辑也可以移动到支持 bean。请记住,在 primefaces 中,有时组件处理得不是很好,你可以尝试然后将它们用作属性而不是像 post

中那样的面

也有可能是你误解了facet的意思。解释它们的最好方法是定义 i 组件的方面。该组件的作者希望为用户提供定义 header 和数据表页脚的可能性。然后,作为 jsf 用户,您可以从其他不同的组件组成 header。您还可以查看此 post,其中还解释了方面。

要补充的另一件事是,将 <h:panelGroup rendered="#{bean.checkValue}"/> 用于呈现逻辑被认为是错误的模式,因为它将在您的代码中生成 <span> 元素。相反,您应该使用用于渲染逻辑的 <ui:fragment rendered="#{bean.checkValue}"/>,它不会产生任何额外的 html 代码