我有一个selectOneMenu来控制应该在数据表中显示的内容。代码如下(我删除了所有不必要的员工):
<ui:composition template="/WEB-INF/templates/BasicTemplate.xhtml">
<ui:define name="content">
<br />
<h:form id="menuform">
<p:selectOneMenu value="#{envMenuBean.currentEnvName}">
<f:selectItems value="#{envMenuBean.envs}" var="env" itemLabel="#{env.name}" itemValue="#{env.name}" />
<p:ajax event="change" update="currentEnvoutput,contentpanel" listener="#{envMenuBean.envChange}" />
</p:selectOneMenu>
<h:outputLabel value="Current Selection: " />
<h:outputText id="currentEnvoutput" style="font-weight:bold" value="#{envMenuBean.currentEnvName}"></h:outputText>
<br />
<p:panel id="contentpanel">
<div id="contentdiv">
<p:dataTable id="gcfiletable" var="row" value="#{gCSelectionBean.dataTableDTO.serverListRows}">
<p:column>
<f:facet name="header">
<h:outputText value="Server Names" />
</f:facet>
<h:outputText value="#{row.serverName}" />
</p:column>
<p:columns value="#{gCSelectionBean.dataTableDTO.machineNamesList}" var="columnName" columnIndexVar="colIndex">
<f:facet name="header">
#{columnName}
</f:facet>
</p:columns>
</p:dataTable>
</div>
</p:panel>
</h:form>
</ui:define>
</ui:composition>
envMenuBean.envChange代码非常简单:
@ManagedBean
@SessionScoped
public class EnvMenuBean {
private String currentEnvName;
public void envChange(AjaxBehaviorEvent event) {
String newValue = (String)((UIOutput)event.getSource()).getValue();
currentEnvName = newValue;
}
}
数据表内容在gCSelectionBean类中生成:
@ManagedBean
@SessionScoped
public class GCSelectionBean {
private GCInstanceDataTableDTO dataTableDTO;
String currentEnvName;
public GCInstanceDataTableDTO getDataTableDTO() {
FacesContext fc = FacesContext.getCurrentInstance();
Application app = fc.getApplication();
ExpressionFactory exp = app.getExpressionFactory();
ValueExpression currEnvNameMenuBeanEL = exp.createValueExpression(fc.getELContext(), "#{envMenuBean.currentEnvName}", String.class);
String currEnvNameMenuBean = (String) currEnvNameMenuBeanEL.getValue(fc.getELContext());
ApplicationConfigs gcReportConfigs = GetAppConfigs.getInstance().getAppConfigs();
for (Environment env : gcReportConfigs.getEnvs()) {
if (env.getName().equalsIgnoreCase(currEnvNameMenuBean)) {
dataTableDTO = new GCInstanceDataTableDTO(env);
currentEnvName = currEnvNameMenuBean;
break;
}
}
return dataTableDTO;
}
}
然而代码
ValueExpression currEnvNameMenuBeanEL = exp.createValueExpression(fc.getELContext(), "#{envMenuBean.currentEnvName}", String.class);
String currEnvNameMenuBean = (String) currEnvNameMenuBeanEL.getValue(fc.getELContext());
在更改之前给出了旧的selectOneMenu值,这使得我的数据表仍然显示旧的表值。但是
<h:outputText id="currentEnvoutput" style="font-weight:bold" value="#{envMenuBean.currentEnvName}"></h:outputText>
可以显示正确的新值。
这使我相信myfaces在处理ajax更改事件之前首先呈现表。当我将JSF2.0实现从myfaces更改为Glassfish时,相同的代码工作正常。
有没有人遇到同样的问题?如何解决这个问题?
答案 0 :(得分:1)
实际更新的currentEnvName
值应该出现在
public void envChange(AjaxBehaviorEvent event) {
System.out.println(currentEnvName );
}
你不必像你那样设置它......
而不是所有这些ValueExpression
内容,您最好使用托管属性
在GCSelectionBean
内添加以下内容:
@ManagedProperty(value = "#{envMenuBean }")
private EnvMenuBean envMenuBean ; //add getter and setter
从envMenuBean obejct ...
访问currentEnvName
这就是全部?
答案 1 :(得分:0)
这似乎与primefaces有关,在将primefaces-3.4-SNAPSHOT的primefaces升级到primefaces-3.4.1之后,问题得到了解决。