我使用JSF 2和primefaces 5.1,我有一个selectOneButton,它有2个值, EN / FR,我想在每次更改语言时收到通知,然后更改页面的区域设置。 现在问题是这个selectOneButton在splitButton中,并且出于某种原因, ajax提交"更改"对于selectOneButton,事件始终返回null,并且它永远不会传递所选的值。
<h:form prependId="false" id="headerForm">
<p:splitButton>
<p:menuitem>
<p:selectOneButton id="langs" value="#{bean.lang}" >
<f:selectItem itemLabel="English" itemValue="en"/>
<f:selectItem itemLabel="Françcais" itemValue="fr"/>
<f:ajax event="change"/>
</p:selectOneButton>
</p:menuitem>
</p:splitButton>
这只是为了测试:
public void setLang(String lang) {
System.out.println("Changed: " + lang);
this.lang = lang;
}
当我将selectOneButton放在p:菜单中作为示例时,它可以正常工作。
答案 0 :(得分:2)
这个问题是双重的。
首先,大多数PrimeFaces组件,特别是那些生成隐藏的HTML输入元素的组件,并通过一堆带有点击监听器的div /列表呈现给最终用户,而不是&#34;纯HTML&#34;输入,要求在ajax提交期间正确处理<p:ajax>
而不是<f:ajax>
。
<p:selectOneButton id="lang" value="#{bean.lang}" >
<f:selectItem itemLabel="English" itemValue="en"/>
<f:selectItem itemLabel="Français" itemValue="fr"/>
<p:ajax />
</p:selectOneButton>
请注意,我省略了event
属性,因为它已经具有正确的默认值,如果是输入则为valueChange
,如果是命令则为action
。 change
的值不一定是正确的默认值,因为某些组件需要click
,尤其是具有固定值的单选按钮和复选框。
在任何情况下,一般建议是,如果您使用PrimeFaces,只需坚持<p:ajax>
。它将使用特定于PrimeFaces的基于jQuery的Ajax API来处理ajax请求而不是JSF本机Ajax API,并且它能够处理PrimeFaces组件。
其次,与<p:splitButton>
关联的JavaScript代码将菜单的HTML表示移动到正文的末尾(为了确保与z-index的最佳交叉浏览器兼容性)。然而,这会导致菜单不再处于某种形式。您可以通过右键单击 Inspect Element (不是查看源!)来查看webbrowser中的HTML DOM树来确认它。您可以通过两种方式解决这个问题:
将表单移动到菜单项内。无论如何,为这个特定要求提交所有其他菜单项是没有意义的。
<p:splitButton>
<p:menuitem>
<h:form id="languageForm">
<p:selectOneButton id="lang" value="#{bean.lang}" >
<f:selectItem itemLabel="English" itemValue="en"/>
<f:selectItem itemLabel="Français" itemValue="fr"/>
<p:ajax />
</p:selectOneButton>
</h:form>
</p:menuitem>
</p:splitButton>
使用<p:ajax partialSubmit="true">
让PrimeFaces Ajax API收集invidivual输入值,而不是搜索<form>
和serializing它(因为有&#39; s会失败)没有形式)。
<h:form id="headerForm">
<p:splitButton>
<p:menuitem>
<p:selectOneButton id="lang" value="#{bean.lang}" >
<f:selectItem itemLabel="English" itemValue="en"/>
<f:selectItem itemLabel="Français" itemValue="fr"/>
<p:ajax partialSubmit="true" />
</p:selectOneButton>
</p:menuitem>
</p:splitButton>
</h:form>