How to fire loadComplete after new row is added in jqgrid?
Asked Answered
M

1

0

I have a custom formatter that fire inside loadComplete of jqgrid. Need the same custom formatter to work when a row is dynamically added too. So i was thinking to call loadComplete() like any normal function. Custom formatter works well when grid is loaded, but does not take effect when a row is added later.

add row dynamically

function addRow(cfgid,cfgname,hostname,osname,cfgDesc,productId,cfgType,updateDate,emailAddress,absolutePath,fileName,productVersion,converted)
{

    var myrow = {cfgId:cfgid, '':'', cfgName:cfgname, hostname:hostname, osname:osname, cfgDesc:cfgDesc, productId:productId,hostname:hostname,cfgType:cfgType,updateDate:updateDate,emailAddress:emailAddress,absolutePath:absolutePath,fileName:fileName,productVersion:productVersion,converted:converted};

    $("#list1").addRowData(cfgid, myrow,"first");
    //$("#list1").loadComplete(); does not work
    $("#list1").trigger("reloadGrid");
    $("#list1").sortGrid('updateDate', true, 'desc');

}

JqGrid

function drawDynamicGrid(xml)
{
    var emptyMsgDiv = $('<div>No configurations loaded</div>');

    var xmlObject=StringtoXML(xml);
    var getColumnIndexByName = function (grid, columnName) {
        var cm = grid.jqGrid('getGridParam', 'colModel'), i = 0, l = cm.length;
        for (; i < l; i += 1) {
            if (cm[i].name === columnName) {
                return i; // return the index
            }
        }
        return -1;
    },
    grid = jQuery("#list1"),
    convertIcon = '<span class="ui-state-default" style="border:0" id="converted"><span class="ui-icon ui-icon-info" style="float: left; margin-right: .3em;"></span></span>',
    iconAlert = '<span class="ui-state-error" style="border:0" id="expired"><span class="ui-icon ui-icon-alert" style="float: left; margin-right: .3em;"></span></span>';
    grid.jqGrid({

      datastr : xml,
      datatype: 'xmlstring',
      colNames:['cfgId','Name', 'Host','Operating System', 'Description','Product', 'Type', 'Last Updated Time','Last Updated By','','','',''],
      colModel:[
          {name:'cfgId',index:'cfgId', width:90, align:"left", hidden:true},
          {name:'cfgName',index:'cfgName', width:80, align:"left", formatter: 'showlink', formatoptions: {baseLinkUrl: '#'} },
          {name:'hostname',index:'hostname', width:70, align:"left"},
          {name:'osname',index:'osname', width:90, align:"left"},
          {name:'cfgDesc',index:'cfgDesc', width:80, align:"left"},
          {name:'productId',index:'productId', width:40, align:"left"},
          {name:'cfgType',index:'cfgType', width:50, align:"left"},
          {name:'updateDate',index:'updateDate',sorttype:'Date', width:120, align:"left"},
          {name:'emailAddress',index:'emailAddress', width:120, align:"left"},
          {name:'absolutePath',index:'absolutePath', width:90, align:"left", hidden:true},
          {name:'fileName',index:'fileName', width:10, align:"left", hidden:true},
          {name:'productVersion',index:'productVersion', width:10, align:"left", hidden:true},
          {name:'converted',index:'converted', width:10, align:"left", hidden:true}
      ],
      pager : '#gridpager',
      rowNum:10,
      rowList:[10,50,100],
      scrollOffset:0,
      height: 'auto',
      emptyrecords: 'No configurations loaded',
      autowidth:true,
      viewrecords:true,
      gridview: true,
      multiselect: true,
      xmlReader: {
          root : "list",
          row: "Response",
          id: "cfgId",
          userdata: "userdata",
          repeatitems: false
      },

      loadComplete: function () {

            var count = grid.jqGrid('getGridParam');
            var ts = grid[0];
            if (ts.p.reccount === 0) {
                grid.hide();
                emptyMsgDiv.show();
            } else {
                grid.show();
                emptyMsgDiv.hide();
            }

            //for showlink and icon alert having date difference more than 90 days
            var iRow, row, trClasses, $cell,
            icfgName = getColumnIndexByName(grid, 'cfgName'),
            iupdateDate = getColumnIndexByName(grid, 'updateDate'),
            iconverted = getColumnIndexByName(grid, 'converted'),

            mygrid = grid[0],
            rows = mygrid.rows,
            cRows = rows.length,
            myLink = function (e) {
                var $td = $(e.target).closest('td'),
                    text = $td.text(),
                    $tr = $td.closest('tr'),
                    rowid = $tr[0].id;
                    goToViewAllPage(rowid);
            };
        for (iRow = 0; iRow < cRows; iRow += 1) {
            row = rows[iRow]; // row.id is the rowid
            trClasses = row.className.split(' ');
            if ($.inArray('jqgrow', trClasses) > 0) {
                // the row is a standard row (only if subGrid:true are used)
                var cellvalue1,firstDate,secondDate;
                $cell = $(row.cells[icfgName]);
                cellvalue1=$(row.cells[iupdateDate]).text();
                firstDate = new Date();
                //console.info(cellvalue1+", "+cellvalue1.length);
                //var cellvalue1="08-18-2011 11:49:01";
                var convertedText=$(row.cells[iconverted]).text();
                if(cellvalue1.length>25)
                {

                    secondDate=new Date();
                    //secondDate = secondDate.substring(0, secondDate.length-3);

                    if(diffOf2Dates(firstDate,secondDate,true)>=expireCondition)
                    {
                        $cell.prepend(iconAlert);
                    }
                    $cell.click(myLink);
                }
                else
                {
                    if(cellvalue1.length!=1)
                    {

                        secondDate = cellvalue1.substring(0, cellvalue1.length-6);
                        if(diffOf2Dates(firstDate,secondDate,false)>=expireCondition)
                        {
                            $cell.prepend(iconAlert);
                        }
                        $cell.click(myLink);
                    }

                    //I want to add this Icon when a new row is added using addRowData
                    if(convertedText=="yes"&&supportEng)$cell.prepend(convertIcon);


                }
            }
        }

        }
    });
    grid.jqGrid('navGrid','#gridpager',{edit:false,add:false,del:false});

    var myGrid = $("#list1");
    $("#cb_"+myGrid[0].id).hide();
    // place div with empty message insde of bdiv
    emptyMsgDiv.insertAfter(grid.parent());

    $("#list1").trigger("reloadGrid");
    $("#list1").sortGrid('updateDate', true, 'desc');
    $("#list1").setGridParam({rowNum:10});

}

Update

Server Response

<list>
  <Response>
    <cfgId>1223</cfgId>
    <cfgName>ld</cfgName>
    <cfgDesc>fhdf</cfgDesc>
    <cfgType>Production</cfgType>
    <fileName>4.xml</fileName>
    <absolutePath>../../../xmlrepository/121/4_ver3.xml</absolutePath>
    <emailAddress>[email protected]</emailAddress>
    <projectId>121</projectId>
    <hostname>abc-dev-01.24hourfit.com</hostname>
    <createDate>2012-12-07 12:15:48.0 IST</createDate>
    <updateDate>2012-12-07 12:15:48.0 IST</updateDate>
    <state>1</state>
    <productId>3</productId>
    <osname>Linux</osname>
    <productVersion>1.0 HotFix5</productVersion>
    <converted>yes</converted>
  </Response>
  <Response>
    <cfgId>1224</cfgId>
    <cfgName>DD</cfgName>
    <cfgDesc>dfsd</cfgDesc>
    <cfgType>Production</cfgType>
    <fileName>2.xml</fileName>
    <absolutePath>../../../xmlrepository/121/2_ver1.xml</absolutePath>
    <emailAddress>[email protected]</emailAddress>
    <projectId>121</projectId>
    <hostname>vkeh-jam</hostname>
    <createDate>2012-12-07 12:21:31.0 IST</createDate>
    <updateDate>2012-12-07 12:21:31.0 IST</updateDate>
    <state>1</state>
    <productId>3</productId>
    <osname>HP-UX</osname>
    <productVersion>5.0</productVersion>
    <converted>no</converted>
  </Response>
</list>

goToViewAllPage function

function goToViewAllPage(rowid)
{
    var pageLoadContent='<table id="detailTable" width="100%"><tbody><tr><td align="center">Please Wait</td></tr><tr><td align="center"><img src="/informaticaCSM/infa9/csm/view/include/images/loading.gif" alt="Loading"/></td></tr></tbody></table>';
    //rowid=rowid.substring(4, rowid.length);
    $("#nextPageLoading").pageLoad({content:pageLoadContent});
    $("#nextPageLoading").css({"cursor":"wait"});
    $("#pageLoadingBackground").css({"cursor":"wait"});

    var rowData = jQuery("#list1").getRowData(rowid); 
    configid = rowData['cfgId'];
    configname=rowData['cfgName'];
    configdesc=rowData['cfgDesc'];
    configenv=rowData['cfgType'];
    filename=rowData['fileName'];
    updatedate=rowData['updateDate'];
    absolutepath=rowData['absolutePath'];
    productname=rowData['productId'];
    productversion=rowData['productVersion'];
    converted=rowData['converted'];

    //emailid=rowData['emailAddress'];
    emailid=logid;

    var form_ref=document.createElement("form");
    form_ref.id="viewform";
    form_ref.name="viewform";
    form_ref.action=redirectMainUrl+"showResult.action";
    form_ref.method="post";
    form_ref.target="_self";
    document.body.appendChild(form_ref);

    var cfgstField = document.createElement("input");
    cfgstField.name="sessiontoken";
    cfgstField.type="hidden";
    cfgstField.value=sessiontoken;
    form_ref.appendChild(cfgstField);

    var cfgidField = document.createElement("input");
    cfgidField.name="cfgid";
    cfgidField.type="hidden";
    cfgidField.value=configid;
    form_ref.appendChild(cfgidField);

    var cfgnameField = document.createElement("input");
    cfgnameField.name="cfgname";
    cfgnameField.type="hidden";
    cfgnameField.value=configname;
    form_ref.appendChild(cfgnameField);

    var cfgdescField = document.createElement("input");
    cfgdescField.name="cfgdesc";
    cfgdescField.type="hidden";
    cfgdescField.value=configdesc;
    form_ref.appendChild(cfgdescField);

    var cfgenvField = document.createElement("input");
    cfgenvField.name="cfgenv";
    cfgenvField.type="hidden";
    cfgenvField.value=configenv;
    form_ref.appendChild(cfgenvField);

    var cfgfileField = document.createElement("input");
    cfgfileField.name="cfgfile";
    cfgfileField.type="hidden";
    cfgfileField.value=filename;
    form_ref.appendChild(cfgfileField);

    var cfgabsField = document.createElement("input");
    cfgabsField.name="absFileName";
    cfgabsField.type="hidden";
    cfgabsField.value=absolutepath;
    form_ref.appendChild(cfgabsField);

    var cfgdateField = document.createElement("input");
    cfgdateField.name="updatedDate";
    cfgdateField.type="hidden";
    cfgdateField.value=updatedate;
    form_ref.appendChild(cfgdateField);

    var cfgproductField = document.createElement("input");
    cfgproductField.name="productname";
    cfgproductField.type="hidden";
    cfgproductField.value=productname;
    form_ref.appendChild(cfgproductField);

    var cfgproductVersionField = document.createElement("input");
    cfgproductVersionField.name="productversion";
    cfgproductVersionField.type="hidden";
    cfgproductVersionField.value=productversion;
    form_ref.appendChild(cfgproductVersionField);

    var projectIdField = document.createElement("input");
    projectIdField.name="projectid";
    projectIdField.type="hidden";
    projectIdField.value=$("#projectId").val();
    form_ref.appendChild(projectIdField);

    var cfgprevPageField = document.createElement("input");
    cfgprevPageField.name="backpage";
    cfgprevPageField.type="hidden";
    cfgprevPageField.value=$("#backPage").val();
    form_ref.appendChild(cfgprevPageField);

    var hiddenEmailField = document.createElement("input");
    hiddenEmailField.setAttribute("type", "hidden");
    hiddenEmailField.setAttribute("name", "emailaddress");
    //hiddenEmailField.setAttribute("value", document.getElementById("usernamespan").innerHTML);
    hiddenEmailField.setAttribute("value", emailid);
    form_ref.appendChild(hiddenEmailField);

    var hiddenEmailField = document.createElement("input");
    hiddenEmailField.setAttribute("type", "hidden");
    hiddenEmailField.setAttribute("name", "fullemailid");
    hiddenEmailField.setAttribute("value", fullEmailId);
    form_ref.appendChild(hiddenEmailField);    

    var hiddenConvertedField = document.createElement("input");
    hiddenConvertedField.setAttribute("type", "hidden");
    hiddenConvertedField.setAttribute("name", "converted");
    hiddenConvertedField.setAttribute("value", converted);
    form_ref.appendChild(hiddenConvertedField);

    setTimeout(function(){
        form_ref.submit();
    }, 10);


}
Mccartney answered 7/12, 2012 at 10:26 Comment(10)
Sorry, but what you currently do is not custom formatter instead of that you modify the content of some rows inside of loadComplete. It reduces the performance of filling of the grid im multiple time. It you have small number of rows you will not see that, but it's still very ineffective. Could you describe what you need to do? I see that you use showlink formatter, but it seems that you modify the results manually. Instead of that you can use real custom formatter and to solve the problem in its the origin.Beebeebe
@Oleg: This is a similar question, which was answered by you long back. See here, It calculates date, if the difference is > 90 days it displays an icon, this was there in the previous question answered by you. The current question puts another icon if value of 1 converted column is "yes", but this does not work if a row is added separately.Mccartney
You have additionally many hidden columns. Do you use there data only inside of loadComplete or you need the data somewhere else? I suppose that you can remove the most of the columns. If needed you can save the data inside of some JavaScript objects instead. Setting of data on the page (even hidden elements) reduce performance of the page.Beebeebe
@Oleg: I use these hidden data even outside the grid. The grid size will not go beyond 100 rows.Mccartney
I study new thing every day too. I would now not implement the things like more as one year before. Could you describe more exactly what kind on modification you need to do and how the links (<a> elements) need be constructed. The part with modifications of dates I didn't understood in your code. How the row of data in the server response looks like?Beebeebe
It's very important to reduce the number of modifications of the HTML page to improve the performance. See the answer for details. It's important to understand that saving of any data on the page is much slowly as saving the same data directly in any JavaScript objects. So my main question: what you try to do? I will try to explain what I mean on an example. The resulting code will be more simple and much quickly.Beebeebe
On click of cfgName column a function is called which submits a form, that redirects the page to another page with some parameters taken from the clicked row in the grid. The cfgName column can be prepended with 2 icons showing help tip 1. 90 days and above, 2. Converted So on loadComplete the grid tries to check each row for converted (from server response if "yes") to display an icon (2) and calculates difference between todays date & createDate, if difference greater than 90 days prepend icon (1)Mccartney
Could you post examples of HTML fragments of the generated links?Beebeebe
@Oleg: inside loadComplete it calls goToViewAllPage() which creates a dynamic form and submits it which in turn redirects to another page with some grid parameters. I updated my question with the goToViewAllPage functionMccartney
@Oleg; HTML fragments for both the icons convertIcon = '<span class="ui-state-default" style="border:0" id="converted"><span class="ui-icon ui-icon-info" style="float: left; margin-right: .3em;"></span></span>', iconAlert = '<span class="ui-state-error" style="border:0" id="expired"><span class="ui-icon ui-icon-alert" style="float: left; margin-right: .3em;"></span></span>'; grid.jqGrid({Mccartney
B
2

I would suggest you to remove the current code from loadComplete to custom formatter. Using of custom formatters, cellattr or rowattr in combination with gridview: true is the most effective way to fill the grid. See the answer for more details.

You can change the definition of 'cfgName' column to the following:

{name: 'cfgName', width: 80, classes: "myLink",
    formatter: function (cellValue, options, rowObject) {
        var converted = rowObject.converted === undefined ?
                $(rowObject).find(">converted").text(): rowObject.converted,
            updateDate = rowObject.updateDate === undefined ?
                $(rowObject).find(">updateDate").text(): rowObject.updateDate;
        return (isAlertedDate(updateDate) ? iconAlert: "") +
            (converted === "yes" ? convertIcon : "") +
            "<span>" + cellValue + "</span>";
    },
    cellattr: function () {
        return " title=\"Click here to go to ViewAllPage\"";
    }}

You can use use your current diffOf2Dates function inside of the implementation of isAlertedDate. Moreover I suggest don't use links (<a>) at all to make the code more easy. Instead of that I use classes: "myLink" and I defined the following CSS

.myLink { text-decoration: underline; cursor: pointer; }

The resulting grid will look exactly as before:

enter image description here

To execute some JavaScript code on click on the link (and even on click in the cell with the link) one can use beforeSelectRow or onCellSelect callback. For example

beforeSelectRow: function (rowid, e) {
    var iCol = $.jgrid.getCellIndex($(e.target).closest("td")[0]);
    if (this.p.colModel[iCol].name === 'cfgName') {
        //alert("GO!!!");
        goToViewAllPage(rowid);
        return false;
    }
}

You can see what I mean on the demo.

Beebeebe answered 7/12, 2012 at 14:30 Comment(1)
oh! god superb.. exactly what is needed. Thanks Oleg for your patience and your descriptive answer :)Mccartney

© 2022 - 2024 — McMap. All rights reserved.