Announcement

Collapse
No announcement yet.
X
  • Filter
  • Time
Clear All
new posts

    ListGrid setCriteria fails after setData is called

    I have a data-bound ListGrid that has an associated Timer that refreshes the ListGrid's data at a set interval. The data on the ListGrid is filtered by a Criteria.

    After the response arrives and does a setData on the ListGrid, the ListGrid's Criteria is nulled and I cannot reset it useing the request's criteria (or a cached copy of the ListGrid's criteria.)

    Ideally, I would like to be able to preserve the ListGrid's criteria regardless if I call setData on it. Failing that, I'd like to be able to reset the ListGrid's criteria from the Criteria used in the request.

    Here is example method to reproduce the problem that I'm seeing:

    Code:
    private VLayout refreshCriteriaTest()
    {
    	final VLayout vlayout = new VLayout();
    	vlayout.setMargin(10);
    	vlayout.setWidth(400);
    	vlayout.setHeight(200);
    	
    	grid = new ListGrid();
    	grid.setDataSource(DataSource.get("PING"));
    	grid.setWidth100();
    	grid.setHeight100();
    
    	Criteria criteria = new Criteria("name", "D");
    
    	grid.setCriteria(criteria);
    	grid.fetchData(criteria);
    	
    	vlayout.addMember(grid);
    	
    	final Timer refresher = new Timer() {
    
    		@Override
    		public void run()
    		{
    			DataSource ds = grid.getDataSource();
    			ds.setShowPrompt(false);
    			ds.fetchData(grid.getCriteria(), new DSCallback() {
    
    				@Override
    				public void execute(DSResponse response, Object rawData, DSRequest request)
    				{
    					SC.logWarn("request criteria:" + request.getCriteria());
    					SC.logWarn("grid criteria:" + grid.getCriteria());
    
    					// This will null the criteria.
    					grid.setData(response.getData());
    					
    					SC.logWarn("grid criteria:" + grid.getCriteria());
    
    					grid.setCriteria(request.getCriteria());
    					// The criteria remains null.
    					SC.logWarn("grid criteria:" + grid.getCriteria());
    				}
    			});
    		}
    		
    	};
    	// Every 15 seconds for sake of example.
    	refresher.scheduleRepeating(15000);
    	
    	return vlayout;
    }
    I'm using the following SC_SNAPSHOT-2011-01-04/PowerEdition Deployment (built 2011-01-04), Firefox 3.6.13, Windows 7

    #2
    When you setData() like this, you're downgrading the ListGrid's dataset from a ResultSet (criteria, load-on-demand and cache sync-aware) to just a RecordList. Instead, form a ResultSet from the returned data, and pass that to setData().

    Comment


      #3
      I'm trying to get a 'flicker-free' refresh of the grid, which is why I used setData method. There's no 'flicker' with setData, but it zaps the criteria because of the "downgrading".

      When I use the ResultSet the criteria is kept, but the grid first clears and then displays "Loading data". Maybe I'm doing something wrong with how I'm using ResultSet?

      Here is what I've changed:
      Code:
      @Override
      public void run()
      {
      	final DataSource ds = grid.getDataSource();
      	ds.setShowPrompt(false);
      	
      	final ResultSet resultset = new ResultSet();
      	resultset.setDataSource(ds);
      	resultset.setCriteria(grid.getCriteria());
      	
      	ds.fetchData(grid.getCriteria(), new DSCallback() {
      
      		@Override
      		public void execute(DSResponse response, Object rawData, DSRequest request)
      		{
      			// Now grid will display "Loading data"
      			grid.setData(resultset);
      		}
      	});
      }
      My goal is flicker-free updates of grid maintaining the criteria.

      Comment


        #4
        What you've done there is create a ResultSet with criteria and no data, and handed that to the grid, discarding the data you just fetched. So then the grid will fetch (redundantly).

        Instead, use the data provided to you in the callback of fetchData() to construct a ResultSet that already has data.

        Comment


          #5
          Ahh! Thank you. I apologize for having you repeat what you said before. This is what I did:

          Code:
          @Override
          public void run()
          {
          	final DataSource ds = grid.getDataSource();
          	ds.setShowPrompt(false);
          	ds.fetchData(grid.getCriteria(), new DSCallback() {
          
          		@Override
          		public void execute(DSResponse response, Object rawData, DSRequest request)
          		{
          			final ResultSet resultset = new ResultSet();
          			resultset.setDataSource(ds);
          			resultset.setCriteria(request.getCriteria());
          			resultset.setAllRows(response.getData());
          			
          			grid.setData(resultset);
          		}
          	});
          }
          Do I need to set in the ResultSet the startRow, endRow, and totalRows somehow for it to be correct for scrolling, etc? Thank you again.
          Last edited by dczech; 11 Mar 2011, 11:22.

          Comment


            #6
            That depends - is the dataset completely loaded? If it's incomplete, pass startRow/endRow to fetchData via the dsRequest, and use resultSet.initialData and initialLength to populate with partial data.

            Comment


              #7
              The dataset is not completely loaded, so I'll need to startRow/endRows in a DSRequest.

              But, I'm not seeing where can I find the existing startRow/endRow on the initial ResultSet assigned to the ListGrid. The only place I've found them is on the DSResponse, but if this is the right place I'm not sure how to use it.

              Should I initially populate the ListGrid in a way other than autoFetchData to keep access to the startRow and endRow?

              Comment


                #8
                You don't really need the original startRow and endRow, you just need to make a decision about what you want to load when you refresh.

                You can look at ResultSet.rowIsLoaded() if you want to base the refresh data on how much was loaded before. Or you can look at the first and last visible row and perhaps add some extra rows around that.

                Comment

                Working...
                X