Announcement

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

    ListGrid can't reorder datasource records via drag-and-drop

    I have a ListGrid similar to some of the examples on the showcase, and while I can reorder records (via drag-and-drop) set by a setData(..) method, I can't reorder records created from an XML data source. Am I setting it up wrong? I have a simple test case below which demonstrates this behavior.

    Thanks!

    Test.java
    Code:
    package test;
    
    import com.google.gwt.core.client.EntryPoint;
    import com.smartgwt.client.widgets.grid.ListGrid;
    import com.smartgwt.client.widgets.layout.VLayout;
    
    public class Test implements EntryPoint {
    	
      public void onModuleLoad() {
        VLayout layout = new VLayout(15);
    	
        final ListGrid grid = new ListGrid();
        grid.setWidth(500);
        grid.setHeight(224);
        grid.setAlternateRecordStyles(true);
        grid.setAutoFetchData(true);
        grid.setCanReorderRecords(true);
        grid.setDataSource(TestDataRecord.getDataSource());
        layout.addMember(grid);
    		
        layout.draw();
      }
    	
    }
    TestDataRecord.java
    Code:
    package test;
    
    import com.google.gwt.core.client.GWT;
    import com.smartgwt.client.data.DataSource;
    import com.smartgwt.client.data.DataSourceField;
    import com.smartgwt.client.data.RestDataSource;
    import com.smartgwt.client.types.DSDataFormat;
    import com.smartgwt.client.types.FieldType;
    import com.smartgwt.client.widgets.grid.ListGridRecord;
    
    public class TestDataRecord extends ListGridRecord {
    	
      public static DataSource getDataSource() {		
        DataSourceField name = new DataSourceField("name", FieldType.TEXT, "Name");
        name.setValueXPath("@name");
        name.setRequired(true);
    		
        RestDataSource datasource = new RestDataSource();
        datasource.setDataURL(GWT.getModuleBaseURL() + "fetch.xml");
        datasource.setDataFormat(DSDataFormat.XML);
        datasource.setXmlRecordXPath("/response/data/category");
        datasource.setFields(name);
        return datasource;
      }
    
    }
    fetch.xml
    Code:
    <response>
      <status>0</status>
        <data>
          <category name="Cat1"/>
          <category name="Cat2"/>
          <category name="Cat3"/>
        </data>
    </response>

    #2
    Try setting a primary key field in the datasource.

    Comment


      #3
      Even i am facing the same problem..pls let me know if u find the solution

      Comment


        #4
        I confirm too !

        * ListGrid.setData(..) is working, we can Drag Drop ReOrder. :)
        * ListGrid.setDataSource(..) + DataSourceTextField.setPrimaryKey(true) is not working. (:

        Setting a primary key field in the datasource is not sufficient...

        Comment


          #5
          What are you expecting the ListGrid to do? It's connected to a remote dataset and has no way to persist the reorder you're doing. If the data is being paged, reordering it locally would create a mismatch between local and remote row numbering.

          You can either:

          1) create a persistent sorted order that the user can modify

          Sort the data on some field, and use updateData() to actually persistently change the data, which will cause the row to move to it's new location.

          2) work with the data locally

          Call DataSource.fetchData() to get a "disconnected" dataset derived from the XML, and apply that to the grid via setData().

          Comment


            #6
            Ahh, I see what you're saying. I'm handling data updates manually, so working with the data locally is fine. But is there a listener to see when a user intended to move a record to a new location, which would tell me the old and new positions or the records that had been changed, so that I could call my update?

            Comment


              #7
              Special field to persist order and display in order ascendant

              In my case, in the ListGridRecord, i have a remote field "orderNumber", by moving i wish get the new row position, to get the new postion before UPDATE dataSource and refresh (fetch) the full ListGrid dataSource.

              I'll see the @Override of DropHandler...

              Comment


                #8
                Drop works, but see the RecordDropHandler recently added to SVN, which is closer to your use case.

                Comment


                  #9
                  That's exactly what I was looking for. Thanks!

                  Comment


                    #10
                    Hy, in a onRecordDrop() i try to :
                    * update all records on ListGrid
                    * fetch ListGrid

                    It's working, but after the final fecth, if i will use again my grid records, i catch this error :
                    Uncaught JavaScript exception [com.google.gwt.dev.shell.HostedModeException: Expected primitive type int; actual value was undefined
                    On line : for( ListGridRecord lgr : countryGrid.getRecords() ) {
                    At method : countryGrid.getRecords()

                    Trace :
                    ** First Pass ReOrder ** :
                    RecordDropHandler event : An event type
                    countryGrid != NULL
                    countryGridgetRecords() != NULL
                    ** Second Pass ReOrder ** :
                    RecordDropHandler event : An event type
                    countryGrid != NULL
                    Uncaught JavaScript exception [com.google.gwt.dev.shell.HostedModeException: Expected primitive type int; actual value was undefined

                    Code:
                    	final ListGrid countryGrid = new ListGrid();  
                    
                            countryGrid.setDataSource(countryDS); 
                            countryGrid.setAutoFetchData(true); 
                    
                            ....
                    
                            countryGrid.addRecordDropHandler(new RecordDropHandler() {
                    
                    			@Override
                    			public void onRecordDrop(RecordDropEvent event) {
                    
                    				System.out.println("RecordDropHandler event : " + event);
                    				
                    				if( countryGrid != null )
                    					System.out.println("countryGrid != NULL");
                    				if( countryGrid.getRecords() != null )
                    					System.out.println("countryGridgetRecords() != NULL");
                    				
                    				for( ListGridRecord lgr : countryGrid.getRecords() ) {
                    					// ReOrder by setAttribute
                    //					lgr.setAttribute("orderId", newOrder);
                    					
                    					countryGrid.updateData(lgr);
                    				}
                    				
                    				countryGrid.invalidateCache();
                    				countryGrid.fetchData();
                    				
                    			}
                            	
                            });
                    The last fetch should not refresh ListGrid cache ?

                    If i comment invalidateCache(), i haven't this error, but no ListGrid visual refresh.

                    Comment


                      #11
                      Try removing the fetchData() line (it's redundant having invalidated cache). Still get the error?

                      Do you see errors reported in the SmartGWT Developer Console?

                      Comment


                        #12
                        Originally posted by Isomorphic
                        Try removing the fetchData() line (it's redundant having invalidated cache). Still get the error?

                        Do you see errors reported in the SmartGWT Developer Console?

                        Hi there... I'm experiencing same problem and have tried all suggestions here but the problem is still there. Does anybody find the answer?

                        Thanks

                        Comment


                          #13
                          SmartGWT3.0

                          I'm trying to implement drag-to-reorder functionality in a ListGrid thats backed by a remote Datasource. The updates are coming through but the oldValues reported are identical to the (new) values.

                          Heres the relevant client-side function:

                          Code:
                            public void onRecordDrop(RecordDropEvent event) {
                          	Scheduler.get().scheduleDeferred(new Scheduler.ScheduledCommand() {
                          
                          		@Override
                          		public void execute() {
                          			try {
                          				int i = 1;
                          				RPCManager.startQueue();
                          				for (ListGridRecord row : listGrid.getRecords()) {
                          					if (Integer.parseInt( row.getAttribute(DISPLAY_ORDER) ) != i) {
                          						// update the node's ordinal value
                          						row.setAttribute(DISPLAY_ORDER, i);
                          						listGrid.updateData(row);
                          					}
                          					i++;
                          				}
                          			} catch (NumberFormatException e) {
                          			} finally {
                          				RPCManager.sendQueue();
                          			}
                          		}
                          	});
                            }
                          This function only updates the DISPLAY_ORDER field if its changed from the original value, hence doesn't touch rows that weren't affected by the re-order.

                          But as I said, the problem is that the update requests that come through to the server (custom Datasource) shows oldValue as actually having the newValue. In addition, all the other fields (attributes) of the row (record) are being sent as new values too eventhough a) they weren't updated and b) they're identical to the values listed in oldValues.

                          I guess I must be using the wrong method to trigger an update to the datasource. Are my expectations correct?

                          Comment


                            #14
                            A change to the Record via setAttribute() is a direct change of locally cached data, so that explains your results. Perform the update with a new Record where you have populating the primary key value and changed fields.

                            Comment


                              #15
                              I understand that setAttribute() may not have been correct. But I don't understand what the replacement would be. Conceptually the row is only being updated, not adding a new one. Also, the DISPLAY_ORDER field of the row isn't the primary key. Can you point me to the method I should be using. Thx.

                              Comment

                              Working...
                              X