我正在使用Primefaces 5.3。
首先,根据这篇文章,我实现了根据 p:selectBooleanCheckbox 的值更改 p:selectOneMenu 可见性的功能:
通过选择复选框启用和禁用组件
到目前为止,如果我使用 h:form,这很有效。
接下来,我想更新 bean 中的值,如在 p:selectOneMenu 中选择的那样。这就是我的问题开始的地方:即使我使用 p:ajax 显式调用侦听器,它也不会被调用。这是我的代码:
<h:panelGrid>
<p:selectOneMenu value="#{schedulerCDIBean.selectedParentTask}" var="parentTask" id="taskDependence" disabled="#{task.dependsOn != 'true'}">
<p:ajax event="change" listener="#{schedulerCDIBean.taskToAddListener}"/>
<f:selectItems id="taskDependenceItems" value="#{schedulerCDIBean.taskWebDataObjectList}" var="item" itemLabel="#{item.taskName}"
itemValue="#{item}" />
<p:column>
<h:outputText value="#{parentTask}"/>
</p:column>
</p:selectOneMenu>
</h:panelGrid>
以下是我启用/禁用选择菜单的方法:
<p:selectBooleanCheckbox id="dependsOnTask" value="#{task.dependsOn}" itemLabel="Depends On">
<p:ajax update="taskDependence" process="@this"/>
</p:selectBooleanCheckbox>
所有这些都位于p:accordionPanel的p:tab中,其中"task"是我的DataObject-List的var。
正如@BalusC在这篇文章中提到的:命令链接/命令按钮/ajax 支持bean操作/侦听器方法未调用(可能的原因:2),
"您不能将多个 UIForm 组件相互嵌套。
因此,如果我删除 h:form 指令,则对 bean 中侦听器的调用将起作用。但是现在,p:selectBooleanCheckbox 的值始终设置为"false",因此组件不会更新为可见。
我在这里找到了一篇文章,其中 OP 有同样的问题,并通过添加 h:form 指令解决了它。
编辑:我的"表单"是一个 ui:composition,开头<ui:composition template="/templates/pages/mainPage.xhtml">
,其中 mainPage.xhtml 包含 h:head,并使用 ui:include 包含"标题.xhtml",并且有一个 h:form。但是这个h:form之前已经关闭了,所以问题不在这里。
好吧,我不想再次添加h:form,因为它会导致未指定的行为。但是,如果我的 p:selectBooleanCheckbox 值设置不正确,我做错了什么?
感谢您的帮助!
更新
问题不在于h:form,因为它实际上不是嵌套的。现在我仍然坚持使用p:selectOneMenu的侦听器,因为它们没有被调用。我还尝试在<p:ajax />
上设置partialSubmit="true"
,到目前为止还没有找到解决方案。
谢谢你们的帮助,伙计们。在您的帮助下,我解决了问题。
就像其他人遇到类似的问题一样,这里有一些事情要检查:
- 在这里查看@BalusC的答案,正如@irieill的答案中也提到的那样。
- 检查您是否有
equals()
和hashCode()
您愿意在 selectOneMenu 中显示的对象。
@irieill的评论中实际上提到了我的情况的解决方案:
[..]不提供适当的转换器不会引发任何异常,但会面临错误消息。因此,请尝试向页面添加
<p:growl autoUpdate="true" />
,看看是否引发了任何转换错误。如果是这样,请将一个 propper 转换器添加到您的selectOneMenu
.
我想,这也是@BalusC在他的可能原因清单的第3点所说的。
另请参阅:如何为<p:pickList>
编写自定义转换器,JSF 2.0中的自定义转换器,PrimeFaces ShowCase:SelectOneMenu
正如@BalusC在这篇文章中提到的:命令链接/命令按钮/ajax 支持bean操作/侦听器方法未调用
另请注意第 1 点。必须用 <h:form />
标记将输入组件括起来。
好吧,我不想再次添加h:form,因为它会导致未指定的行为。
据我了解,您滥用了标签,或者您不了解如何使用它。只需将整个页面(或至少所有输入组件)包含在一个<h:form />
标签中,它就可以工作。
更新您的问题,该页面代码还包含您放置<h:form />
标签的行。