4 Replies Latest reply on Dec 4, 2008 11:07 AM by nbelaevski

    rich:scrollableDataTable is not rerendering ok

    josuemb

      When i change the table contents (using the "rerender" option from a commandButton) the table does not render well. The header is not showing its contents and the columns are bad formed.

      The commandButton changes partially the information of one column and "refresh" the data.

      The a4j:log component show:

      debug[13:05:20,129]: Update part of page for Id: j_id24:tablaBienes:0:hcb_4 successful
      debug[13:05:20,129]: Update page part from call parameter for ID j_id24:tablaBienes:0:hcb_5
      debug[13:05:20,129]: call getElementById for id= j_id24:tablaBienes:0:hcb_5
      debug[13:05:20,130]: Replace content of node by replaceChild()
      debug[13:05:20,131]: search for elements by name 'script' in element div
      debug[13:05:20,131]: Scripts in updated part count : 0
      debug[13:05:20,132]: Update part of page for Id: j_id24:tablaBienes:0:hcb_5 successful
      debug[13:05:20,132]: Update page part from call parameter for ID j_id24:tablaBienes:0:hcb_6
      debug[13:05:20,132]: call getElementById for id= j_id24:tablaBienes:0:hcb_6
      debug[13:05:20,133]: Replace content of node by replaceChild()
      debug[13:05:20,134]: search for elements by name 'script' in element div
      debug[13:05:20,134]: Scripts in updated part count : 0
      debug[13:05:20,134]: Update part of page for Id: j_id24:tablaBienes:0:hcb_6 successful
      debug[13:05:20,135]: Update page part from call parameter for ID j_id24:tablaBienes:0:hcb_7
      debug[13:05:20,135]: call getElementById for id= j_id24:tablaBienes:0:hcb_7
      debug[13:05:20,136]: Replace content of node by replaceChild()
      debug[13:05:20,136]: search for elements by name 'script' in element div
      debug[13:05:20,137]: Scripts in updated part count : 0
      debug[13:05:20,137]: Update part of page for Id: j_id24:tablaBienes:0:hcb_7 successful
      debug[13:05:20,137]: Update page part from call parameter for ID j_id24:tablaBienes:0:hcb_8
      debug[13:05:20,138]: call getElementById for id= j_id24:tablaBienes:0:hcb_8
      debug[13:05:20,139]: Replace content of node by replaceChild()
      debug[13:05:20,139]: search for elements by name 'script' in element div
      debug[13:05:20,140]: Scripts in updated part count : 0
      debug[13:05:20,140]: Update part of page for Id: j_id24:tablaBienes:0:hcb_8 successful
      debug[13:05:20,140]: Update page part from call parameter for ID j_id24:tablaBienes:0:hcb_9
      debug[13:05:20,141]: call getElementById for id= j_id24:tablaBienes:0:hcb_9
      debug[13:05:20,142]: Replace content of node by replaceChild()
      debug[13:05:20,142]: search for elements by name 'script' in element div
      debug[13:05:20,143]: Scripts in updated part count : 0
      debug[13:05:20,143]: Update part of page for Id: j_id24:tablaBienes:0:hcb_9 successful
      debug[13:05:20,143]: Update page part from call parameter for ID j_id24:tablaBienes:s
      debug[13:05:20,143]: call getElementById for id= j_id24:tablaBienes:s
      debug[13:05:20,144]: Replace content of node by replaceChild()
      debug[13:05:20,145]: search for elements by name 'script' in element input
      debug[13:05:20,145]: Scripts in updated part count : 0
      debug[13:05:20,145]: call getElementById for id= org.ajax4jsf.oncomplete
      debug[13:05:20,146]: Update part of page for Id: j_id24:tablaBienes:s successful
      debug[13:05:20,146]: call getElementById for id= ajax-view-state
      debug[13:05:20,146]: Hidden JSF state fields: [object HTMLSpanElement]
      debug[13:05:20,147]: Namespace for hidden view-state input fields is undefined
      debug[13:05:20,147]: search for elements by name 'input' in element span
      debug[13:05:20,148]: Replace value for inputs: 19 by new values: 1
      debug[13:05:20,149]: Input in response: javax.faces.ViewState
      debug[13:05:20,150]: Found same input on page with type: hidden
      debug[13:05:20,150]: Found same input on page with type: hidden
      debug[13:05:20,151]: search for elements by name 'INPUT' in element span
      debug[13:05:20,151]: Replace value for inputs: 19 by new values: 0
      debug[13:05:20,151]: call getElementById for id= _ajax:data
      debug[13:05:20,153]: call getElementById for id= _ajax:data
      debug[13:05:20,153]: call getElementById for id= _A4J.AJAX.focus
      debug[13:05:20,154]: No focus information in response
      debug[13:05:20,387]: Evaluate script replaced area in document: //<![CDATA[ window.Richfaces_ScrollableGrid_j_id24_tablaBienes = new ClientUI.controls.grid.ScrollableGrid({'hideWhenScrolling':false,'rowsCount':0,'columnsCount':10,'ids':['valuador','lote','ubicación','comentarios','descripcion','unidad','candidad','fotos','mandato','numero'] ,'onSortAjaxUpdate':function(event){A4J.AJAX.Submit('_viewRoot','j_id24',event,{'oncomplete':function(request,event,data){window.Richfaces_ScrollableGrid_j_id24_tablaBienes.onSortComplete(request,event,data)},'similarityGroupingId':'j_id24:tablaBienes','parameters':{'j_id24:tablaBienes':'j_id24:tablaBienes','j_id24:tablaBienes:sortIndex':event.index,'j_id24:tablaBienes:sortOrder':event.order,'j_id24:tablaBienes:sortStartRow':event.startRow,'j_id24:tablaBienes:sortColumn':event.column} ,'actionUrl':'/carasa-lb-admin/richfaces/listarBienes.jsf'} ); return false;},'selectionInput':'j_id24:tablaBienes:s','selectedClass':'','normalizedId':'j_id24_tablaBienes','client_id':'j_id24:tablaBienes','activeClass':''} ); ; // ]]>
      error[13:05:20,388]: . Error message: $(this.client_id + "_rows_input") is null


      The code for my Facelet is:

      <ui:composition xmlns="http://www.w3.org/1999/xhtml"
      xmlns:ui="http://java.sun.com/jsf/facelets"
      xmlns:h="http://java.sun.com/jsf/html"
      xmlns:f="http://java.sun.com/jsf/core"
      xmlns:a4j="http://richfaces.org/a4j"
      xmlns:rich="http://richfaces.org/rich"
      xmlns:c="http://java.sun.com/jstl/core"
      xmlns:fn="http://java.sun.com/jsp/jstl/functions">


      .alineacion-derecha {
      text-align:right;
      }
      .alineacion-centrada {
      text-align:center;
      }
      .scrolls{
      width:300px;
      height:200px;
      overflow:auto;
      }


      <a4j:form name="frmListarBienes">
      <h:inputHidden id="claveBienActual" value="#{consultarFotosBean.claveBienActual}" />

      Seleccione la Subasta y presione el botón "Listar Bienes"
      <h:outputLabel style="font-weight:bold;font-size:small">Subasta:</h:outputLabel>
      <a4j:outputPanel id="subastaPanel" layout="block">
      <h:selectOneMenu id="subasta" name="subasta"
      value="#{listarBienesBean.cveSubastaSeleccionada}"
      valueChangeListener="#{listarBienesBean.onChangeSubasta}">
      <f:selectItems value="#{listarBienesBean.subastasAbiertas}" />
      </h:selectOneMenu>
      <rich:spacer width="20px"/>
      <h:outputLabel style="font-weight:bold;font-size:small">Ubicación:</h:outputLabel>
      <h:selectOneMenu id="localidad" name="localidad"
      value="#{listarBienesBean.cveLocalidadSeleccionada}"
      rendered="#{not empty listarBienesBean.cveSubastaSeleccionada}">
      <f:selectItems value="#{listarBienesBean.localidadesPorSubasta}" />
      </h:selectOneMenu>

      <a4j:commandButton id="btnListarBienes" name="btnListarBienes"
      action="#{listarBienesBean.listarBienes}"
      value="Listar Bienes"
      reRender="bienesPanel"
      style="margin: 9px 0px 5px;" />
      <rich:spacer width="20px"/>
      <a4j:status>
      <f:facet name="start">
      <h:outputText style="font-weight:bold;font-size:small" value="Cargando..."/>
      </f:facet>
      </a4j:status>
      </a4j:outputPanel>

      <a4j:outputPanel id="bienesPanel">

      Lista de Bienes
      <a4j:outputPanel id="tablaBienesPanel">
      <rich:scrollableDataTable id="tablaBienes"
      rowKeyVar="rkv" frozenColCount="1" height="400px"
      width="850px" columnClasses="col"
      value="#{listarBienesBean.bienesPorSubasta}"
      var="bien" sortMode="single"
      binding="#{listarBienesBean.tabla}"
      sortOrder="#{listarBienesBean.orden}"
      selection="#{listarBienesBean.seleccion}"
      first="0"
      rows="0">
      <rich:column id="numero" styleClass="alineacion-centrada" width="45px" >
      <f:facet name="header"><h:outputText styleClass="headerText" value="Bien" /></f:facet>
      <h:outputText value="#{bien[0]}" />
      </rich:column>
      <rich:column id="lote" styleClass="alineacion-centrada" width="35px" >
      <f:facet name="header"><h:outputText styleClass="headerText" value="Lote" /></f:facet>
      <h:outputText value="#{fn:length(fn:split(bien[1],'@'))>=3?fn:split(bien[1],'@')[2]:'No asignado'}" />
      </rich:column>
      <rich:column id="candidad" styleClass="alineacion-derecha" width="55px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Cantidad" /></f:facet>
      <h:outputText value="#{bien[2]}" />
      </rich:column>
      <rich:column id="descripcion" width="200px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Descripción" /></f:facet>
      <h:outputText value="#{bien[3]}" />
      </rich:column>
      <rich:column id="fotos" styleClass="alineacion-centrada" width="30px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Fotos" /></f:facet>
      <h:outputText value="#{bien[4]}" />
      <a4j:commandLink action="#{consultarFotosBean.inicializarFotografias}" oncomplete="javascript:Richfaces.showModalPanel('mostrarFotos', {claveBienActual: #{empty bien[0]?'':bien[0]}});" reRender="mostrarFotos">
      <a4j:actionparam name="claveBienActual" value="#{bien[0]}" assignTo="#{consultarFotosBean.claveBienActual}" />
      <h:graphicImage height="16px" value="/images/ico_MostrarFotos.png"/>
      </a4j:commandLink>
      </rich:column>
      <rich:column id="valuador" width="150px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Valuador" /></f:facet>
      <h:outputText value="#{(empty bien[5])?'No asignado':bien[5]}" />
      </rich:column>
      <rich:column id="mandato" width="70px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Mandato" /></f:facet>
      <h:outputText value="#{bien[6]}" />
      </rich:column>
      <rich:column id="ubicación" width="80px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Ubicación" /></f:facet>
      <h:outputText value="#{bien[7]}" />
      </rich:column>
      <rich:column id="unidad" width="50px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Unidad" /></f:facet>
      <h:outputText value="#{empty bien[8]?'No asignado':bien[8]}" />
      </rich:column>
      <rich:column id="comentarios" width="100px">
      <f:facet name="header"><h:outputText styleClass="headerText" value="Comentarios" /></f:facet>
      <h:outputText value="#{empty bien[9]?'No asignado':bien[9]}" />
      </rich:column>
      </rich:scrollableDataTable>
      </a4j:outputPanel>
      <h:outputLabel style="font-weight:bold;font-size:small">Seleccione el valuador:</h:outputLabel>
      <rich:spacer width="20px"/>
      <h:selectOneMenu id="valuador" value="#{listarBienesBean.idValuadorSeleccionado}">
      <f:selectItems value="#{listarBienesBean.valuadores}" />
      </h:selectOneMenu>
      <rich:spacer width="20px"/>
      <a4j:commandButton id="btnSeleccionarValuador"
      action="#{listarBienesBean.asignarValuadorABienesSeleccionados}"
      value="Asignar Valuador"
      reRender="tablaBienesPanel"
      style="margin: 9px 0px 5px;" />

      </a4j:outputPanel>
      </a4j:form>

      <rich:modalPanel id="mostrarFotos" autosized="false" resizable="true"
      keepVisualState="false" width="700" height="640">
      <f:facet name="controls">
      <h:panelGroup>
      <h:graphicImage value="/images/close.png" style="cursor:pointer" id="hidelinkFotos"/>
      <rich:componentControl for="mostrarFotos" attachTo="hidelinkFotos" operation="hide" event="onclick"/>
      </h:panelGroup>
      </f:facet>
      <f:facet name="header">
      <h:outputText value="FotografÃÂas para el bien: #{consultarFotosBean.claveBienActual}"/>
      </f:facet>
      <a4j:outputPanel id="fotosPanel" layout="block">
      <a4j:form id="frmFotografiasSel">
      <rich:dataGrid id="fotografiasBienSeleccionado" value="#{consultarFotosBean.fotosBienActual}" var="fotografia" first="0" columns="1" elements="1" width="200px">
      <rich:panel bodyClass="pbody">
      <f:facet name="header">
      <h:outputText value="Archivo: #{fotografia[2]}"></h:outputText>
      </f:facet>
      <h:panelGrid columns="1">
      <a4j:mediaOutput element="img" cacheable="false" session="true"
      createContent="#{consultarFotosBean.crearFotografia}" value="#{fotografia[1]}" mimeType="image/jpeg" />
      </h:panelGrid>
      </rich:panel>
      <f:facet name="footer">
      <rich:datascroller boundaryControls="auto" fastControls="auto" />
      </f:facet>
      </rich:dataGrid>
      <a4j:commandButton id="btnCerrarFotos"
      onclick="javascript:Richfaces.hideModalPanel('mostrarFotos');"
      value="Cerrar"
      reRender="listaDeBienes"
      style="margin: 9px 0px 5px;" />
      </a4j:form>
      </a4j:outputPanel>
      </rich:modalPanel>
      <a4j:log popup="false" level="ALL" style="width: 800px; height: 300px;"></a4j:log>
      </ui:composition>


      The code for my bean is:

      @Controller(value = "listarBienesBean")
      @Scope("session")
      public class ListarBienesBean {

      @Resource
      private SubastaService subastaService;
      @Resource
      BienService bienService;
      @Resource
      UsuarioService usuarioService;
      private String claveBienActual;
      private Set llaves = new HashSet();
      private Integer filaActual;
      private SimpleSelection seleccion = new SimpleSelection();
      private UIScrollableDataTable tabla;
      private SortOrder orden = new SortOrder();
      private int pagina;
      private List subastasAbiertas = new ArrayList();

      private List<Object[]> bienesSeleccionados = new ArrayList<Object[]>();
      private List<Object[]> bienesPorSubasta = new ArrayList<Object[]>();
      private String cveSubastaSeleccionada;
      private List localidadesPorSubasta = new ArrayList();
      private String cveLocalidadSeleccionada;
      private List valuadores = new ArrayList();
      private Integer idValuadorSeleccionado;
      private List fotosBienActual = new ArrayList();

      public ListarBienesBean() {
      SortField[] fields = {new SortField("0", true)};
      orden.setFields(fields);
      }

      /**
      * @param subinfoService the subinfoService to set
      */
      @Required
      public void setSubastaService(SubastaService subinfoService) {
      this.subastaService = subinfoService;
      }

      /**
      * @param bienService the bienService to set
      */
      @Required
      public void setBienService(BienService bienService) {
      this.bienService = bienService;
      }

      /**
      * @param usuarioService the usuarioService to set
      */
      @Required
      public void setUsuarioService(UsuarioService usuarioService) {
      this.usuarioService = usuarioService;
      }

      /**
      * @return the cveSubastaSeleccionada
      */
      public String getCveSubastaSeleccionada() {
      return cveSubastaSeleccionada;
      }

      /**
      * @param cveSubastaSeleccionada the cveSubastaSeleccionada to set
      */
      public void setCveSubastaSeleccionada(String cveSubastaSeleccionada) {
      this.cveSubastaSeleccionada = cveSubastaSeleccionada;
      }

      /**
      * @return the cveLocalidadSeleccionada
      */
      public String getCveLocalidadSeleccionada() {
      return cveLocalidadSeleccionada;
      }

      /**
      * @param cveLocalidadSeleccionada the cveLocalidadSeleccionada to set
      */
      public void setCveLocalidadSeleccionada(String cveLocalidadSeleccionada) {
      this.cveLocalidadSeleccionada = cveLocalidadSeleccionada;
      }

      /**
      * @return the idValuadorSeleccionado
      */
      public Integer getIdValuadorSeleccionado() {
      return idValuadorSeleccionado;
      }

      /**
      * @param idValuadorSeleccionado the idValuadorSeleccionado to set
      */
      public void setIdValuadorSeleccionado(Integer idValuadorSeleccionado) {
      this.idValuadorSeleccionado = idValuadorSeleccionado;
      }

      public List getSubastasAbiertas() {
      synchronized (this) {
      if (subastasAbiertas.isEmpty()) {
      //Consulta las subastas no cerradas desde la base de datos.
      final ArrayList<Object[]> subastasTemp =
      ClassUtils.cast(subastaService.getSubastasNoCerradas());
      //Agrega las subastas consultadas desde la base de datos al combo.
      for (Object[] subastaTemp : subastasTemp) {
      subastasAbiertas.add(
      new SelectItem(subastaTemp[0],
      (String)subastaTemp[1]));
      }
      if (!subastasAbiertas.isEmpty()) {
      cveSubastaSeleccionada = (String) subastasAbiertas.get(0).getValue();
      }
      }
      }
      return subastasAbiertas;
      }

      public List getLocalidadesPorSubasta() {
      synchronized (this) {
      if (localidadesPorSubasta.isEmpty() &&
      !cveSubastaSeleccionada.isEmpty()) {
      //Consulta localidades de la subasta seleccionada.
      final ArrayList localidadesTemp =
      (ArrayList) subastaService.getLocalidadesPorSubasta(cveSubastaSeleccionada);
      //Agrega las localidades consultadas desde la base de datos al combo.
      for (String localidad : localidadesTemp) {
      localidadesPorSubasta.add(
      new SelectItem(localidad, localidad.trim()));
      }
      if (!localidadesPorSubasta.isEmpty()) {
      cveLocalidadSeleccionada = (String) localidadesPorSubasta.get(0).getValue();
      }
      }
      }
      return localidadesPorSubasta;
      }

      public void onChangeSubasta(javax.faces.event.ValueChangeEvent event) {
      localidadesPorSubasta.clear();
      getLocalidadesPorSubasta();
      }

      public List<Object[]> getBienesPorSubasta() {
      return bienesPorSubasta;
      }

      public List getValuadores() {
      synchronized (this) {
      if (valuadores.isEmpty()) {
      //Consulta la lista de valuadores.
      final List<Object[]> valuadoresTemp = ClassUtils.cast(usuarioService.getUsuariosByIdPerfil(Constantes.USUARIO_PERFIL_VALUADOR));
      //Agrega los valuadores consultadas desde la base de datos a la lista.
      for (Object[] valuador : valuadoresTemp) {
      valuadores.add(
      new SelectItem(valuador[0], (String)valuador[1]));
      }
      if (!valuadores.isEmpty()) {
      idValuadorSeleccionado = (Integer) valuadores.get(0).getValue();
      }
      }
      }
      return valuadores;
      }

      /**
      * Carga la subasta seleccionada.
      * @return true en caso exitoso, false en caso contrario
      * @throws HumanTechSolutionsWebException
      */
      public String listarBienes() throws HumanTechSolutionsWebException {
      synchronized (this) {
      try {
      bienesPorSubasta.clear();
      //Consulta las subastas no cerradas desde la base de datos,
      //tomando como parámetros la subasta y la localidad.
      bienesPorSubasta = ClassUtils.cast(bienService.findBienesPorSubastayUbicacion(cveSubastaSeleccionada, cveLocalidadSeleccionada));
      } catch (Exception e) {
      throw new HumanTechSolutionsWebException("Error al ejecutar ListarBienesBean.listarBienes()", e);
      }
      }
      return null;
      }

      public SimpleSelection getSeleccion() {
      return seleccion;
      }

      public void setSeleccion(SimpleSelection seleccion) {
      this.seleccion = seleccion;
      }

      public String consultarBienesSeleccionados() throws HumanTechSolutionsWebException {
      try {
      getBienesSeleccionados().clear();
      if (getSeleccion().isSelectAll()) {
      getBienesSeleccionados().addAll(bienesPorSubasta);
      } else {
      Iterator iterator = getSeleccion().getKeys();
      while (iterator.hasNext()) {
      Object key = iterator.next();
      tabla.setRowKey(key);
      if (tabla.isRowAvailable()) {
      getBienesSeleccionados().add((Object[]) tabla.getRowData());
      }
      }
      }
      } catch (Exception e) {
      throw new HumanTechSolutionsWebException("Error al ejecutar ListarBienesBean.consultarBienesSeleccionados()", e);
      }
      return null;
      }

      @Transactional(readOnly=false)
      public String asignarValuadorABienesSeleccionados() throws HumanTechSolutionsWebException {
      try {
      Usuario valuador = (Usuario) usuarioService.findPersistentObjectByKey(Usuario.class, idValuadorSeleccionado);
      EstadoBien estadoBienAsignado = (EstadoBien) usuarioService.findPersistentObjectByKey(EstadoBien.class, Constantes.ESTADO_BIEN__ASIGNADO);
      //Consulta los bienes seleccionados.
      consultarBienesSeleccionados();
      //Recorre la lista de bienes seleccionados.
      for( Object[] bienSel : getBienesSeleccionados() ) {
      final Bien objBienSel = (Bien) bienService.findPersistentObjectByKey(Bien.class, (String)bienSel[0]);
      objBienSel.setUsuario(valuador);
      objBienSel.setEstadoBien(estadoBienAsignado);
      objBienSel.setFechaUltMod(Calendar.getInstance().getTime());
      bienService.updatePersistentObject(objBienSel);
      }
      listarBienes();
      } catch (Exception e) {
      throw new HumanTechSolutionsWebException("Error al ejecutar ListarBienesBean.asignarValuadorABienesSeleccionados()", e);
      }
      return null;
      }

      public List getFotosBienActual() {
      return fotosBienActual;
      }

      public void setFotosBienActual(final List fotosBienActual) {
      this.fotosBienActual = fotosBienActual;
      }

      public List<Object[]> getBienesSeleccionados() {
      return bienesSeleccionados;
      }

      public void setBienesSeleccionados(final ArrayList<Object[]> bienesSeleccionados) {
      this.bienesSeleccionados = bienesSeleccionados;
      }

      public boolean isHayBienesSeleccionados() {
      return !bienesSeleccionados.isEmpty();
      }

      public UIScrollableDataTable getTabla() {
      return tabla;
      }

      public void setTabla(UIScrollableDataTable tabla) {
      this.tabla = tabla;
      }

      public int getPagina() {
      return pagina;
      }

      public void setPagina(int pagina) {
      this.pagina = pagina;
      }

      public SortOrder getOrden() {
      return orden;
      }

      public void setOrden(SortOrder orden) {
      this.orden = orden;
      }

      public String getClaveBienActual() {
      return claveBienActual;
      }

      public void setClaveBienActual(String claveBienActual) {
      this.claveBienActual = claveBienActual;
      }

      public Integer getFilaActual() {
      return filaActual;
      }

      public void setFilaActual(Integer filaActual) {
      this.filaActual = filaActual;
      }

      public Set getLlaves() {
      return llaves;
      }

      public void setLlaves(Set llaves) {
      this.llaves = llaves;
      }
      }