Brandon Minton
Brandon Minton

Reputation: 1004

jqGrid row(s) deletion

I have a button used to delete a row when checked that calls the built in function 'delRowData'. Simple enough until you want to remove an array of rows/multiple rows (as in the built-in variable 'selarrrow'). Does anyone have a better answer than the horrible muck I've came up with (eg. modifying core jqGrid code)??

Here's my code:

        $("#deleteButton").click(function(){ 
            var gr = jQuery("#myGrid").jqGrid('getGridParam','selarrrow'); 
            var su=jQuery("#myGrid").jqGrid('delRowData',gr.toString()); 
            (su) ? '' : alert("Already deleted or not in list"); 
        }); 

and now for the really nasty part of modifying core code in jquery.jqGrid.min.js:

delRowData:function(f){
for(var m=0,max=f.length;m<max;m++){
    var j=false,i,c;
    this.each(function(){
        var e=this;
        if(i=e.rows.namedItem(f[m])){
            b(i).remove();
            e.p.records--;
            e.p.reccount--;
            e.updatepager(true,false);
            j=true;
            if(e.p.multiselect){
                c=b.inArray(f[m],e.p.selarrrow);
                c!=-1&&e.p.selarrrow.splice(c,1)
            }
            if(f==e.p.selrow)e.p.selrow=null
        }else return false;
        if(e.p.datatype=="local"){
            var k=e.p._index[f[m]];
            if(typeof k!="undefined"){
                e.p.data.splice(k,1);
                e.refreshIndex()
            }
        }
    });
}
        /*if(e.p.altRows===true&&j){
            var n=e.p.altclass;b(e.rows).each(function(a){
                a%2==1?b(this).addClass(n):b(this).removeClass(n)
            })
        }*/

    return j
}

Is there a better way to do this?

/* New details **/
So even if we iterate over the given jqGrid array 'selarrrow' and remove the the rows one by one while using jqGrid's default 'delRowData' function:

$("#deleteButton").click(function(){ 
    $.each($("#myGrid").jqGrid('getGridParam','selarrrow'), function(index, value) {
        console.log($("#myGrid").jqGrid('getGridParam','selarrrow'));
        if ($("#myGrid").jqGrid('delRowData', value)) {
            console.log($("#myGrid").jqGrid('getGridParam','selarrrow'));
            console.log(value);
        } 
        else{
            console.log($("#myGrid").jqGrid('getGridParam','selarrrow'));
            console.log(value);
        }
    });
}); 

you'll see the code does not perform correctly and we have to go back to look at the jqGrid core-code function of 'delRowData'. The problem now lies with how it tackles the array. Here's the function un-minified:

delRowData:function(f){
    var j=false,i,c;
    this.each(function(){
        var e=this;
        if(i=e.rows.namedItem(f)){
            b(i).remove();
            e.p.records--;
            e.p.reccount--;
            e.updatepager(true,false);
            j=true;
            if(e.p.multiselect){
                c=b.inArray(f,e.p.selarrrow);
                //c!=-1&&e.p.selarrrow.splice(c,1)
            }
            if(f==e.p.selrow)
                e.p.selrow=null
            }else 
                return false;
            if(e.p.datatype=="local"){
                var k=e.p._index[f];
                if(typeof k!="undefined"){
                    e.p.data.splice(k,1);
                    e.refreshIndex()
            }
        }
        if(e.p.altRows===true&&j){
            var n=e.p.altclass;
            b(e.rows).each(function(a){
                a%2==1?b(this).addClass(n):b(this).removeClass(n)
            })
        }
    });
    return j
}

The problem is the commented out line in the middle of the function. I really wanted to avoid hacking core-code but it seems you have to do so unless you have a better idea.

Upvotes: 3

Views: 17767

Answers (3)

Faiyaz
Faiyaz

Reputation: 1411

jqGrid removes the deleted row from selarrrow - arrow also. One of the way to do multiple row deletion is using

var selrows = $('#grid').jqGrid('getGridParam', 'selarrrow');

while (selrows.length > 0)
{
  $('#grid').delRowData(selrows[0]);
}

Upvotes: 2

Michael Saffitz
Michael Saffitz

Reputation: 186

The problem is that getGridParam is returning a reference to the selected rows (selarrrow). You then use this to iterate through a delete rows from the grid, which modifies selarrow on the line you identified. This changes the collection you're iterating over, so that subsequent iterations no longer point to the correct values.

You can either use $.MakeArray to iterate through a copy of the selected arrays, or iterate from the tail of the array, for example:

var ids = $('#grid').getGridParam('selarrrow');
for (  var i = ids.length-1; i>=0; i--) {
  $('#grid').delRowData(ids[i]);
}

There's a discussion on this at: http://www.trirand.com/blog/?page_id=393/bugs/delrowdata-bug-on-grid-with-multiselect/

Upvotes: 5

Gary Green
Gary Green

Reputation: 22395

Why not use each outside, instead of hacking the core?

$("#deleteButton").click(function(){
  var errors = [];
  jQuery("#myGrid").jqGrid('getGridParam','selarrrow').each(function(index, value) {
    if (!jQuery("#myGrid").jqGrid('delRowData', value)) errors.push(value);
  });
  if (errors.length)
  {
    alert('Already deleted or not in list on row(s): ' + errors.join(', ')); 
  }
}); 

Upvotes: 0

Related Questions