p:仍然需要selectOneMenu值

时间:2013-07-07 00:41:54

标签: jsf primefaces jstl selectonemenu

在我的xhtml页面中,我有两个依赖的selectOneMenu,第二个填充了一个ajax调用。这是jsf代码片段:

   <h:panelGrid columns="2" cellpadding="5">
     <h:outputLabel value="Dirección:" for="direccion"/>
       <p:inputText id="direccion" value="#{datosInstitucion.institucion.direccion}" required="true" label="Dirección"/>
       <h:outputLabel value="Departamento:" for="departamento"/>
       <p:selectOneMenu id="departamento" value="#{datosInstitucion.idDepartamento}" required="true" label="Departamento">
          <f:selectItem itemLabel="Seleccione el departamento" itemValue="#{null}"/>
          <c:forEach items="#{datosInstitucion.departamentos}" var="departamento">
             <f:selectItem itemLabel="#{departamento.nombre}" itemValue="#{departamento.id}"/>
          </c:forEach>
          <f:ajax render="municipio" listener="#{datosInstitucion.cargarMunicipios()}"/>
       </p:selectOneMenu>
       <h:outputLabel value="Municipio:" for="municipio"/>
       <p:selectOneMenu id="municipio" value="#{datosInstitucion.idMunicipio}"                                           required="true" label="Municipio">
          <f:selectItem itemLabel="Seleccione el municipio" itemValue="#{null}"/>
             <c:forEach items="#{datosInstitucion.municipios}" var="municipio">
                <f:selectItem itemLabel="#{municipio.nombre}" itemValue="#{municipio.id}"/>
             </c:forEach>
       </p:selectOneMenu>
   </h:panelGrid>

此代码片段位于primefaces向导组件内,因此当按下“下一个”按钮时,即使有值设置,也会导致第二个selectOneMenu出现验证错误。

可能导致此行为的原因是什么?

相关的支持bean代码:

@ManagedBean(name = "datosInstitucion")
@ViewScoped
public class DatosInstitucion implements Serializable{

    @EJB
    private Instituciones instituciones;

    @EJB
    private Parametros parametros;

    @Inject
    private Mensajes mensajes;

    private List<Departamento> departamentos;
    private List<Municipio> municipios;
    private Map<Integer, Departamento> mapaDepartamentos;
    private Integer idDepartamento;
    private Integer idMunicipio;

    private Institucion institucion;

    @PostConstruct
    private void inicializar(){
        this.mapaDepartamentos = new HashMap<>();
        this.departamentos = parametros.consultarDepartamentos();
        for(Departamento departamento : departamentos){
            this.mapaDepartamentos.put(departamento.getId(), departamento);
        }
        this.prepararInstitucion();
    }

    private void prepararInstitucion(){
        this.institucion = new Institucion();
        this.institucion.setResponsable(new Persona());
    }

    public Institucion getInstitucion() {
        return institucion;
    }

    public List<Departamento> getDepartamentos(){
        return departamentos;
    }

    public TipoIdentificacion[] getTiposIdentificacion(){
        return TipoIdentificacion.deResponsables();
    }

    public Integer getIdDepartamento() {
        return idDepartamento;
    }

    public void setIdDepartamento(Integer idDepartamento) {
        this.idDepartamento = idDepartamento;
    }

    public Integer getIdMunicipio() {
        return idMunicipio;
    }

    public void setIdMunicipio(Integer idMunicipio) {
        this.idMunicipio = idMunicipio;
    }

    public void cargarMunicipios(){
        idMunicipio = null;
        if(idDepartamento != null){
            this.municipios = mapaDepartamentos.get(idDepartamento).getMunicipios();
        }else{
            this.municipios = Collections.emptyList();
        }
    }

    public List<Municipio> getMunicipios() {
        return municipios;
    }

    public void confirmar(){
        this.instituciones.guardar(institucion);
        this.mensajes.exito("La institución ha sido registrada en el sistema");
        this.prepararInstitucion();
    }
}

1 个答案:

答案 0 :(得分:1)

这是因为您正在使用JSTL <c:foreach>和JSF。 JSTL与JSF的生命周期很重要。在构建视图时执行JSTL,而在呈现视图时执行JSF。这两者并不是彼此同步的。在您的情况下,您需要使用<f:selectItems>而不是<c:foreach>

替换:

<c:forEach items="#{datosInstitucion.municipios}" var="municipio">
      <f:selectItem itemLabel="#{municipio.nombre}" itemValue="#{municipio.id}"/>
</c:forEach>

使用:

<f:selectItems value="#{datosInstitucion.municipios}" 
    var="municipio" itemLabel="#{municipio.nombre}" 
    itemValue="#{municipio.id}"/>

如需更多阅读,建议您阅读以下answer