Start Building Professional
Web Apps Today


 
Categories Question details Back To List
Question  posted by Ed on Apr 18, 2009 20:42
open dhtmlx forum
Drag and drop beween grids with sendData()

Hello,

What I have is a little complicated, so I'll do my best to explain it.

I have two grids set up on my page... the left grid is full of static values that don't change and is loaded when the page is displayed. The right grid is initialized empty, but is filled by dragging values from the left grid over to the right one. The grid on the right has an extra editable cell on it that can be changed by the user. As each drag happens I do several things:

1. Update the height of the right hand grid
2. Change the editable cell value on the new row to a default value
3. Reset the grid id numbers in the right hand grid and renumber the first column to match via:
for (var i=0; i<schedulegrid.getRowsNum(); i++)
            {
// The alerts are helping me to see what's happening
                var oldid = schedulegrid.getRowId(i);
         schedulegrid.setRowId(i,i+1);
                 schedulegrid.cells2(i,0).setValue(i+1);
                alert('Index: '+i+' - Old: '+oldid+' - New: '+schedulegrid.getRowId(i));
            }
4. Set all the rows of the grid to updated via:
for(var i=1;i<=schedulegrid.getRowsNum(); i++)
            {
                alert(schedulegrid.cells(i,0).getValue()+' - '+i+' out of '+schedulegrid.getRowsNum()+' update...');
                dp.setUpdated(i,true);
            }
5. Finally I do dp.sendData();


I have found that if I drag over the rows from the left side to the right side IN ORDER that the Data Processor works just fine. If I drag them out of order, or if I drag more rows on the right side than exist on the left side it dies with a childNode undefined error in IE or a "r is null" error in Firefox. The data processor is initialized to the correct grid, and all of the alerts I have seem to be returning the data I would expect.

It seems like a row ID error in the sendData function, but I don't understand how the row IDs could be incorrect given that I reset them all everytime a row is moved, the reset is done and correct before I ever call sendData, and I set all the rows to updated without any kind of error.

I have the pro version, but it's pretty old - v16_80512.

Just for completeness, here is my grid and dataprocessor initialization:

var dp = new dataProcessor('updateschedulegrid.php');
    dp.setTransactionMode("POST",true);
    dp.setUpdateMode("off");
    dhtmlxError.catchError("LoadXML", function(){ return false; });
    schedulegrid = new dhtmlXGridObject('schedulegridbox');
    schedulegrid.setImagePath("javascript/dhtmlgrid/imgs/");
    schedulegrid.setEditable(true);
    schedulegrid.setSkin("mt");
    schedulegrid.setHeader(",,Chain Run,Run Time,Start Time");
    schedulegrid.setInitWidths("15,60,*,67,75");
    schedulegrid.setColTypes("ro,ro,ro,ro,ed");
    schedulegrid.setColAlign("left,left,left,left,left");
    schedulegrid.setColSorting("na,na,na,na,str");
    schedulegrid.enableResizing("false,false,true,true,true");
    schedulegrid.enableDragAndDrop(true);
    schedulegrid.enableMercyDrag(true);
    schedulegrid.setDragBehavior('sibling');
    schedulegrid.enableEditEvents(true,true,true);
    //schedulegrid.attachEvent("onRowSelect",doRowSelect);
    schedulegrid.attachEvent("onEditCell",doCellEdit);
    schedulegrid.attachEvent("onDrop",doDrop);
    schedulegrid.init();
    schedulegrid.setSerializationLevel(false,false,false,false,false,true);
dp.init(schedulegrid);

And here is the grid on the left side that I'm dragging from, just in case it matters:

chainrungrid = new dhtmlXGridObject('chainrungridbox');
    chainrungrid.setImagePath("javascript/dhtmlgrid/imgs/");
    chainrungrid.setEditable(false);
    chainrungrid.setSkin("mt");
    chainrungrid.setHeader(",,Chain Run,Run Time");
    chainrungrid.setInitWidths("15,35,*,67");
    chainrungrid.setColTypes("ro,ro,ro,ro");
    chainrungrid.setColAlign("left,left,left,left");
    chainrungrid.setColSorting("na,na,na,na");
    chainrungrid.enableResizing("false,false,true,true");
    chainrungrid.enableDragAndDrop(true);
    chainrungrid.enableMercyDrag(true);
    chainrungrid.init();

I've been pulling my hair out over this all day. Thank you for your time.
Answer posted by Support on Apr 20, 2009 01:35
>>for (var i=0; i<schedulegrid.getRowsNum(); i++) 
>>    schedulegrid.setRowId(i,i+1); 

This is a not safe code. For example you have next grid

row1, ID=1
row2, ID=2
row3, ID=3

With you logic, after first loop iteration, IDs will be changed to the 

row1, ID=2 // i+1
row2, ID=2
row3, ID=3

There will be two rows with ID = 2 , so there are two rows with equal ID , which can cause problems on next loop iterations 

You can try to change your code as

for (var i=0; i<schedulegrid.getRowsNum(); i++) 
  schedulegrid.setRowId(i,"temp_"+i)); 
for (var i=0; i<schedulegrid.getRowsNum(); i++) {
  schedulegrid.setRowId(i,i+1); 
  schedulegrid.cells2(i,0).setValue(i+1); 
}

With such approach ID duplication will be prevented and problems during data sending will be resolved as well. 



Answer posted by Ed on Apr 20, 2009 18:05
Sorry, but I think I posted a new question rather than updating this old one.  I'll repost the question here.

With the new code you've supplied, I'm still getting the same error:

r is null
dhtmlxdataprocessor.js line 26

The alerts I had in my code always showed the id number I would expect after renumbering the rows, and never contained any duplicates.
Answer posted on Apr 21, 2009 05:58
Latest version of dhtmlxdataprocessor.js for grid 1.6 sent by email. It has few fixes, none of which directly related to your issue, but still maybe somehow related. 
Please try to use it instead of original one. 
Answer posted by Ed at duskrider.com on Apr 21, 2009 21:50
I haven't received the download yet, I might've given you an incorrect address or the mail might've been blocked by my server.  Can you re-send it to ed at duskrider.com and ezenisek at nmsu.edu, just to make sure I get it?

Thank you.
Answer posted on Apr 22, 2009 20:37
Ok,

I tried the new file and I'm still getting the error.  I added an alert to the sendData() function in dhtmlxdataprocessor.js just to see what the rowId that was actually getting passed to the processor (line 391 is where I added it), and the row ID that is being passed to sendData is the OLD row id from the grid on the left.  So if I drag row 1 on the left to be the first row on the right, it works.  If I drag row 2 on the left to be the first row (row 1) on the right, it breaks because the sendData function is looking for row 2... the original row ID. 

Even when I explicitly do a sendData(i) where i = 1 (after dragging the second row in the left grid to the first row on the right grid), the rowId in the dataprocessor alerts that the rowId it has is 2.. matching the old id from the left side.

In another case, I drag three rows, in order, from the left side to the right side.  All three times it updates with no error.  On my application there are times when the user might want to drag the same row over twice, which is fine... putting the same record in two locations.  If I drag over one of the three rows again, to make a fourth brand new row on the right, the sendData alerts 1, 2, 3, 11240457634449 even though the alerts on my page say 1, 2, 3, 4 for the rowIds.

How can I make sure that the sendData function is getting the brand new row Ids that I've assigned and have it ignore the old row id numbers? 

Answer posted by Support on Apr 23, 2009 06:02
The problem can be caused by next two issues

a) moment when sendData called - if command was called before rowID change - it will send update with old ID ( it will result in js error after response received, because ID in response differs from one in grid. 
b) there was some problem with ID changing logic, so it was not called against all rows

The code which you are using now seems correct, it change IDs for all rows and send data only after that. 

>>alerts 1, 2, 3, 11240457634449 
When duplicate ID detected during d-n-d , grid automatically set new unique ID for element. So its original row ID after d-n-d.

>>Even when I explicitly do a sendData(i) 
You are using "send - all" behavior, so grid collect data for all updated rows, ignoring provided parameter. 
Grid hears inner events and store IDs or updated|added|deleted rows in inner collection ( setUpdated method ) 
When ID changed in grid, grid generates special event, on which dataprocessor changes IDs in its collection. 

You can try to add the next code to the grid's init
grid.attachEvent("onRowIdChange",function(a,b){
           alert("change id from "+a+" to"+b);
})
If all goes correctly it will show all changed ids

Also, latest build of grid 1.6 sent by email, please try to update dhtmlxgrid.js with provided one.