I am using free jqGrid 4.12.1. I want to add, edit and delete rows in the grid and wish to make server side calls for each operation.
I have added editurl and 'actions' formatter as below,
{
name: "actions",
width: 100,
formatter: "actions",
formatoptions: {
keys: true,
editOptions: {},
addOptions: {},
delOptions: {}
}
}
I am adding 'inlineNav' as below,
$("#itemList").jqGrid('inlineNav',"#itemListPager",
{
edit: true,
add: true,
del: true,
search: true,
searchtext: "Search",
addtext: "Add",
edittext: "Edit",
deltext: "Delete"
},
{
closeOnEscape: true, //Closes the popup on pressing escape key
reloadAfterSubmit: true,
drag: true,
url: "${pageContext.request.contextPath}/billing/saveItem",
errorfunc: function (rowId, resp) {
alert(resp);
},
afterSubmit: function (response, postdata) {
if (response.responseText == "") {
$(this).jqGrid('setGridParam', { datatype: 'json' }).trigger('reloadGrid'); //Reloads the grid after edit
return [true, '']
}
else {
$(this).jqGrid('setGridParam', { datatype: 'json' }).trigger('reloadGrid'); //Reloads the grid after edit
return [false, response.responseText]//Captures and displays the response text on th Edit window
}
},
editData: {
EmpId: function () {
var sel_id = $('#itemList').jqGrid('getGridParam', 'selrow');
var value = $('#itemList').jqGrid('getCell', sel_id, '_id');
return value;
}
}
},
{
closeAfterAdd: true, //Closes the add window after add
url: "${pageContext.request.contextPath}/billing/saveItem",
afterSubmit: function (response, postdata) {
if (response.responseText == "") {
$(this).jqGrid('setGridParam', { datatype: 'json' }).trigger('reloadGrid')//Reloads the grid after Add
return [true, '']
}
else {
$(this).jqGrid('setGridParam', { datatype: 'json' }).trigger('reloadGrid')//Reloads the grid after Add
return [false, response.responseText]
}
}
},
{ //DELETE
closeOnEscape: true,
closeAfterDelete: true,
reloadAfterSubmit: true,
url: "${pageContext.request.contextPath}/billing/saveItem",
drag: true,
afterSubmit: function (response, postdata) {
if (response.responseText == "") {
$("#itemList").trigger("reloadGrid", [{ current: true}]);
return [false, response.responseText]
}
else {
$(this).jqGrid('setGridParam', { datatype: 'json' }).trigger('reloadGrid');
return [true, response.responseText]
}
},
delData: {
EmpId: function () {
var sel_id = $('#itemList').jqGrid('getGridParam', 'selrow');
var value = $('#itemList').jqGrid('getCell', sel_id, '_id');
return value;
}
}
},
{//SEARCH
closeOnEscape: true
}
);
The 'inlineNav' added above has no effect because no server side call is made on adding a new row or deleting existing row. The server side call is made only in case of edit, and that call too does not happen through 'inlineNav' code above. Because even if i remove 'inlineNav' code the server side call is still made to the 'editurl'.
So how can i make server side calls on adding/editing/deleting rows and also pass parameters to these calls. I will really appreciate if someone can point me to a working example somewhere. Thanks
UPDATE:-
I have removed 'actions' formatter and modified code to look as below,
<script type="text/javascript">
var dataGrid = $('#itemList');
var firstClick = true;
$(document).ready(function () {
$('#action').click(function () {
if (!firstClick) {
$("#itemList").setGridParam({datatype:'json'}).trigger("reloadGrid");
}
firstClick = false;
$("#itemList").jqGrid({
url: "${pageContext.request.contextPath}/billing/medicines",
datatype: "json",
//styleUI : 'Bootstrap',
mtype: "POST",
autowidth: true,
shrinkToFit: true,
sortname: "Id",
sortorder: "asc",
loadBeforeSend: function(jqXHR) {
jqXHR.setRequestHeader("X-CSRF-TOKEN", $("input[name='_csrf']").val());
},
postData: {
},
loadError: function (jqXHR, textStatus, errorThrown) {
alert('HTTP status code: ' + jqXHR.status + '\n' +
'textStatus: ' + textStatus + '\n' +
'errorThrown: ' + errorThrown);
alert('HTTP message body (jqXHR.responseText): ' + '\n' + jqXHR.responseText);
},
colNames: ["Id", "Item Type", "Item Code", "Unit", "Stock", "Batch No.", "Expiry Date", "Quantity Per Unit", "Price"],
colModel: [
{ name: "itemId", width: 35, align: "left", sorttype:"int", search: false},
{ name: "itemType", width: 100, align: "left", editable: true},
{ name: "itemCode", width: 120, align: "left", editable: true},
{ name: "unit", width: 70, align: "left", search: false, editable: true},
{ name: "availableQuantity", width: 55, align: "left", search: false, formatter: "number", editable: true},
{ name: "batchNumber", width: 80, align: "left", search: false, editable: true},
{ name: "expiryDate", width: 80, align: "left", search: false, sorttype: "date", editable: true, formatoptions: {srcformat:'d/m/Y', newformat:'d/m/Y'}},
{ name: "quantityPerUnit", width: 80, align: "left", search: false, formatter: "number", editable: true},
{ name: "price", width: 55, align: "left", search: false, formatter: "number", editable: true}
],
pager: "#itemListPager",
rowNum: 50,
rowList: [50, 100, 150, 200],
rownumbers: true,
rownumWidth: 25,
sortname: "id",
sortorder: "desc",
viewrecords: true,
height: '100%',
loadonce: true,
//gridview: true,
autoencode: true,
editurl: "${pageContext.request.contextPath}/billing/saveItem",
caption: "Item List",
ondblClickRow: function(rowId){}
}).navGrid('#itemListPager',{add:false,edit:false,del:true});
$("#itemList").jqGrid('filterToolbar', {autoSearch: true, stringResult: true, searchOnEnter: false, defaultSearch: 'cn'});
$("#itemList").jqGrid('gridResize', { minWidth: 450, minHeight: 150 });
var saveparameters = {
"successfunc" : null,
"url" : "${pageContext.request.contextPath}/billing/saveItem",
"extraparam" : {},
"aftersavefunc" : null,
"errorfunc": null,
"afterrestorefunc" : null,
"restoreAfterError" : true,
"mtype" : "POST"
};
var editparameters = {
"keys" : false,
"oneditfunc" : null,
"successfunc" : null,
"url" : "${pageContext.request.contextPath}/billing/editItem",
"extraparam" : {},
"aftersavefunc" : null,
"errorfunc": null,
"afterrestorefunc" : null,
"restoreAfterError" : true,
"mtype" : "POST"
};
var parameters = {
edit: true,
editicon: "ui-icon-pencil",
add: true,
addicon:"ui-icon-plus",
save: true,
saveicon:"ui-icon-disk",
cancel: true,
cancelicon:"ui-icon-cancel",
addParams : saveparameters,
editParams : editparameters
};
$("#itemList").jqGrid('inlineNav',"#itemListPager", parameters);
});
});
</script>
The sample json dada is as,
[
{"itemDetailId":1,"itemId":1,"itemType":"Medicine","itemCode":"Aler-Dryl","itemDesc":"Aler-Dryl","batchNumber":"batch1","expiryDate":"18/02/2017","unit":"tablet","subUnit":"tablet","availableQuantity":120.0,"quantityPerUnit":60.0,"price":122.0},
{"itemDetailId":2,"itemId":2,"itemType":"Medicine","itemCode":"Benadryl","itemDesc":"Benadryl","batchNumber":"batch1","expiryDate":"18/02/2017","unit":"ml","subUnit":"ml","availableQuantity":60.0,"quantityPerUnit":120.0,"price":90.0}
]
Now the url specified in editparameters and saveparameters is getting invoked on editing and adding a row respectively.
Please suggest if above approach is a good one. Also how can we set a request header before edit or save data is posted to server. And i can not find anything like deleteparameters similar to editparameters and saveparameters so that i can use delete specific parameters.
UPDATE 2:-
I could successfully set a request header before server side code is invoked on add/edit row using following code,
$.ajaxSetup({
beforeSend: function (jqXHR, settings) {
jqXHR.setRequestHeader("X-CSRF-TOKEN", $("input[name='_csrf']").val());
}});
UPDATE 3:-
Cleaned up code as per Oleg's suggestions as below. But in the strict mode i am getting JS error now - "Uncaught ReferenceError: saveparameters is not defined"
<script type="text/javascript">
$(document).ready(function () {
"use strict";
var dataGrid = $('#itemList');
var firstClick = true;
$('#action').click(function () {
if (!firstClick) {
$("#itemList").setGridParam({datatype:'json'}).trigger("reloadGrid");
}
firstClick = false;
$("#itemList").jqGrid({
url: "${pageContext.request.contextPath}/billing/medicines",
datatype: "json",
mtype: "POST",
autowidth: true,
loadBeforeSend: function(jqXHR) {
jqXHR.setRequestHeader("X-CSRF-TOKEN", $("input[name='_csrf']").val());
},
colNames: ["Id", "Item Type", "Item Code", "Unit", "Stock", "Batch No.", "Expiry Date", "Quantity Per Unit", "Price"],
colModel: [
{ name: "itemId", width: 35, align: "left", sorttype:"int", search: false, editable: false, key: true},
{ name: "itemType", width: 100, align: "left"},
{ name: "itemCode", width: 120, align: "left"},
{ name: "unit", width: 70, align: "left", search: false},
{ name: "availableQuantity", width: 55, align: "left", search: false, formatter: "number",},
{ name: "batchNumber", width: 80, align: "left", search: false},
{ name: "expiryDate", width: 80, align: "left", search: false, sorttype: "date", formatoptions: {srcformat:'d/m/Y', newformat:'d/m/Y'}},
{ name: "quantityPerUnit", width: 80, align: "left", search: false, formatter: "number"},
{ name: "price", width: 55, align: "left", search: false, formatter: "number"}
],
cmTemplate: {editable: true},
pager: true,
rowNum: 50,
rowList: [50, 100, 150, 200],
rownumbers: true,
rownumWidth: 25,
sortname: "itemType",
sortorder: "asc",
forceClientSorting: true,
viewrecords: true,
height: '100%',
loadonce: true,
//gridview: true,
autoencode: true,
editurl: "${pageContext.request.contextPath}/billing/saveItem",
caption: "Item List"
//ajaxRowOptions: { beforeSend: myTokenSetting }, loadBeforeSend: myTokenSetting where var myTokenSetting = function(jqXHR) { jqXHR.setRequestHeader("X-CSRF-TOKEN", $("input[name='_csrf']").val()); }
}).navGrid({add:false,edit:false,del:true});
$("#itemList").jqGrid('filterToolbar', {autoSearch: true, stringResult: true, searchOnEnter: false, defaultSearch: 'cn'});
$("#itemList").jqGrid('gridResize', { minWidth: 450, minHeight: 150 });
var saveparameters = {
"successfunc" : null,
"url" : "${pageContext.request.contextPath}/billing/saveItem",
"extraparam" : {},
"aftersavefunc" : null,
"errorfunc": null,
"afterrestorefunc" : null,
"restoreAfterError" : true,
"mtype" : "POST"
};
var editparameters = {
"keys" : false,
"oneditfunc" : null,
"successfunc" : null,
"url" : "${pageContext.request.contextPath}/billing/editItem",
"extraparam" : {},
"aftersavefunc" : null,
"errorfunc": null,
"afterrestorefunc" : null,
"restoreAfterError" : true,
"mtype" : "POST"
};
var parameters = {
edit: true,
editicon: "ui-icon-pencil",
add: true,
addicon:"ui-icon-plus",
save: true,
saveicon:"ui-icon-disk",
cancel: true,
cancelicon:"ui-icon-cancel",
addParams : saveparameters,
editParams : editparameters
};
$("#itemList").jqGrid('inlineNav',parameters);
$.ajaxSetup({
beforeSend: function (jqXHR, settings) {
alert('Before Row Send');
jqXHR.setRequestHeader("X-CSRF-TOKEN", $("input[name='_csrf']").val());
}});
});
});
</script>
You should examine the options of inlineNav to find out that you use absolutely wrong options:
jQuery("#grid_id").jqGrid('inlineNav', pagerid, parameters);
where parameters have the form
{
edit: true,
editicon: "ui-icon-pencil",
add: true,
addicon: "ui-icon-plus",
save: true,
saveicon: "ui-icon-disk",
cancel: true,
cancelicon: "ui-icon-cancel",
addParams: {useFormatter : false},
editParams: {}
}
You use the options of another method navGrid
jQuery("#grid_id").jqGrid('navGrid', '#gridpager', {parameters},
prmEdit, prmAdd, prmDel, prmSearch, prmView);
which allows to use form editing.
You wrote that you want to use both formater: "actions" andinlineNav. Thus you would have to provide some options of inline editing twice. I would recommend you to read [the wiki article](https://github.com/free-jqgrid/jqGrid/wiki/New-style-of-usage-options-of-internal-methods). It describes the problems with the usage of form editing usingformatter: "actions"andnavGridtogether. The usage of inline editing have very close problems. You will have to provideaddParamsandeditParamsproperties ofinlineNavand the corresponding options offormatter: "actions"` (see here). To make the code more readable and simple free jqGrid provides another form of editing options.
You can specify all inline editing options inside of inlineEditing option of jqGrid, additional specific options of inlineNav method (if required) in navOptions or in inlineNavOptions, the options of Delete operation in formDeleting and so on. Moreover reloadGrid have the option fromServer: true to restore the original value of datatype ("json", "jsonp", "xml", ...) which you used. You can use reloadGridOptions: { fromServer: true } option of form editing or formDeleting to force reloading from the server.
Moreover your existing code contains many very suspected parts with _id and EmpId. I would strictly recommend you to include the example of format of input JSON data which you use to fill the grid. If you want to use EmpId as the name of rowid why you use _id instead? The code fragment like
EmpId: function () {
var sel_id = $('#itemList').jqGrid('getGridParam', 'selrow');
var value = $('#itemList').jqGrid('getCell', sel_id, '_id');
return value;
}
shows that the current rowid seems be wrong and _id column contains correct information which you need as rowid under the name EmpId.
You can for example use prmNames: { id: "EmpId"} and to add key: true to the column _id. The property key: true in the column _id will inform jqGrid to use the value from the column _id as the rowid and prmNames: { id: "EmpId"} will rename default id property used in Edit and Delete to EmpId. Thus jqGrid will automatically send EmpId parameter with the value from _id column during Delete and Edit operations to the server.
Probably you can remove unneeded column _id from the grid too (at least if you hold the column hidden), but I need to see input data of jqGrid to say you exact options of jqGrid which you can use.
I'm sure that you can essentially reduce your existing code and make it more readable using free jqGrid options, but you have to review your existing code carefully. I suggest you to start with the usage of correct rowid and elimination of all hidden columns which you use. Free jqGrid provides additionalProperties feature which structure is very close to the structure of colModel, but the corresponding properties of input data will be saved in the local data only and not placed in DOM of the table. I can explain all more clear if you would post your existing colModel, jsonReader and example of JSON response returned from the server (1-2 rows of data with dummy data would be enough).
The search button works on the first click, but once it is closed either by clicking the X (close button) or by running a search (setting to close after search) it does not open, there are also no errors in the console so I am unable to determine what is wrong and how to fix it.
var previouslySelectedRow = null;
var rowIsSelected = null;
var previousRowIsSelected = null;
var currentRowId;
var currentCount;
var cancelEditing = function(theGrid) {
var lrid;
if (typeof previouslySelectedRow !== "undefined") {
// cancel editing of the previous selected row if it was in editing state.
// jqGrid hold intern savedRow array inside of jqGrid object,
// so it is safe to call restoreRow method with any id parameter
// if jqGrid not in editing state
theGrid.jqGrid('restoreRow', previouslySelectedRow);
// now we need to restore the icons in the formatter:"actions"
lrid = $.jgrid.jqID(previouslySelectedRow);
$("tr#" + lrid + " div.ui-inline-edit").show();
$("tr#" + lrid + " div.ui-inline-save, " + "tr#" + lrid + " div.ui-inline-cancel").hide();
}
};
var parsedResult = JSON.parse(DecodeAscii(result));
ShowDebugNotification("DEBUG INFO(" + ajaxCall + "): <br />" + result, false);
$("#productsTable").jqGrid({
data: parsedResult,
datatype: "local",
loadonce: true,
height: 'auto',
marginLeft: 'auto',
colNames: [
'Product Id', 'Add', 'Product Name', 'Product Code', 'Customer Price'
],
colModel: [
{ name: 'Id', width: 0, hidden:true },
{ name: "actions", template: "actions", width: 50, formatoptions:{
delbutton: false,
editbutton: false
} },
{ name: 'Name', index: 'Name', width: 550, search: true, searchoptions:{sopt:['eq','bw','bn','cn','nc','ew','en']} },
{ name: 'ProductCode', index: 'ProductCode', width: 150, search: true, searchoptions:{sopt:['eq','bw','bn','cn','nc','ew','en']} },
{ name: 'Price', index: 'Price', width: 100, search: false, formatter: 'currency', formatoptions:{decimalSeparator:".", thousandsSeparator: ",", decimalPlaces: 2, prefix: "$"}}
],
rowNum: 15,
rowList: [5, 10, 15, 20],
pager: true,
gridView: true,
viewrecords: true,
iconSet: "jQueryUI",
sortname: 'Name',
sortorder: 'asc',
inlineEditing: { keys: false },
actionsNavOptions: {
addToCarticon: "ui-icon-cart",
addToCarttitle: "Add item to the cart",
custom: [
{ action: "addToCart", position: "first", onClick: function (options) {
var rowData = $('#productsTable').getRowData(options.rowid);
var cartButton = $(".ui-icon", "#jAddToCartButton_"+options.rowid);
if(cartButton.hasClass("ui-icon-cancel")){
cart.shift(rowData);
cartButton.removeClass("ui-icon-cancel");
cartButton.addClass("ui-icon-cart");
}
else if(cartButton.hasClass("ui-icon-cart")){
cart.push(rowData);
cartButton.removeClass("ui-icon-cart");
cartButton.addClass("ui-icon-cancel");
}
}
}]
},
loadComplete: function() {
$("#add-product-dialog-loading-message").hide();
$(".spinner").hide();
$("#add-product-dialog-form").dialog("open");
//for each object in cart
//if prodcut ID matches product Id in product
//grid then set button to a cancel icon
if(cart.length !== 0){
var cartIds = [];
var jsonCart = JSON.stringify(cart);
var parsedJsonCart = JSON.parse(jsonCart);
var productsInCart = $.grep(parsedJsonCart, function(el, i){
cartIds.push(el.Id);
});
var currentRows = $('#productsTable').getRowData();
var shownProductsThatAreInCart = $.grep(currentRows, function (el, i) {
return $.inArray(el.Id, cartIds) !== -1;
});
if(shownProductsThatAreInCart.length > 0){
var rowIds = $(this).jqGrid('getDataIDs');
$.each(rowIds, function(k, v) {
rowData = $('#productsTable').getRowData(v);
if($.inArray(rowData['Id'], cartIds) !== -1){
alert("Matched Product:\nRowData['id'] = " + rowData['Id'] + "\nto\nProduct in cart: " + cartIds.Id);
$(".ui-icon", "#jAddToCartButton_"+v).removeClass("ui-icon-cart");
$(".ui-icon", "#jAddToCartButton_"+v).addClass("ui-icon-cancel");
}
});
}
}
},
gridComplete: function() {
}
});
$("#productsTable").jqGrid("navGrid", {edit:false,add:false,del:false},
{},// use default settings for edit
{},// use default settings for add
{},// delete instead that del:false we need this
{multipleSearch:false,overlay:false,ignoreCase:true,closeAfterSearch:true,closeOnEscape:true,showQuery:true});
I don't think its a bug as I have seen many demos demonstrating how it is supposed to work, I am guessing I have a mis-configuration, please have a look over my code and help determine the issue.
One thing to keep in mind is I am getting the data to load the grid via an ajax call that returns json, all manipulation is done on the client, there is no posting data back to server at all.
Thank you!
The main problem is the combination of Searching options which you use:
{
multipleSearch: false, // it's default and can be removed
overlay: false, // !!! the option make the problem
ignoreCase: true, // it's not exist at all
closeAfterSearch: true,
closeOnEscape: true,
showQuery: true
}
The usage of the option overlay: false is bad because it makes another option toTop: true not working and the Searching dialog will be placed as the children of jQuery UI Dialog. If you remove the option then one can work with the Searching Dialog more easy and the second problem (a bug in calculation of position of jqGrid Searching Dialog) will not exist. Look at the modified demo:
https://jsfiddle.net/OlegKi/su7mf5k9/3/
UPDATED: It seems one have the problem in creating modal jqGrid dialog inside of modal jQuery UI dialog. The problem could be solved by removing modal: true option from the outer jQuery UI dialog. See https://jsfiddle.net/OlegKi/su7mf5k9/3/
In general one could create hybrid solution which changes the type of jQuery UI dialog from modal to non-modal dynamically, but it could be tricky https://jsfiddle.net/OlegKi/su7mf5k9/5/
Trying to sort a grid with custom sort. I am building jqgrid with dynamic columns and data. Everything works well except sorting of one of the column. I am using javax.json to build the json and I am using jqgrid 4.7.0. Here is the grid code:
var resultsGrid = $("#resultsGrid");
var url = "grid/GridDataController?action=runSearch&searchText="+getSearchText()+"&_ts"+$.now();
var csvUrl = "grid/GridDataController?action=downloadCsv&_ts"+$.now();
var gridPagerId="#resultsPager";
var drawSearchResultsGrid = function(colNames,colModel,data) {
resultsGrid.disableSelection(); //disales highlioghting cells outside selection like ghosting.
resultsGrid.jqGrid({
url: url,
datatype: 'jsonstring',
loadonce: true,
mtype: "GET",
height: 300,
width: 700,
colNames: colNames,
colModel: colModel,
datastr : data,
rowNum: 100000,
sortname: "invid",
sortorder: "asc",
rownumbers: true,
viewrecords: true,
pager: gridPagerId,
pginput : false,
pgbuttons : false,
viewrecords : false,
gridview: true,
autoencode: true,
onSelectRow : function(id) {
logMessage("row selected ["+id+"]");
},
loadComplete: function(data) {
logMessage("load completed");
},
ondblClickRow : function(rowid) {
logMessage("Double clicked");
$(escapeColon("#contentForm:viewPropertiesButton")).click();
}
});
// Set navigator with search enabled.
resultsGrid.jqGrid('navGrid',gridPagerId,{add:false,edit:false,del:false,search:false,refresh:false});
// add custom button to export the data to excel
resultsGrid.jqGrid('navButtonAdd',gridPagerId,{
caption:"Export",
onClickButton : function () {
resultsGrid.jqGrid('excelExport',{"url":csvUrl});
}
});
}; //end drawResultGrid function
//get grid config...
$.ajax({
type: "GET",
url: url,
data: "",
dataType: "json",
success: function(response)
{
if (response.result == "0")
{
logMessage("Drawing results grid...");
drawSearchResultsGrid(response.colNames,response.colModel,response.data);
resizeGrid();
logMessage("Results grid drawing done.");
}
else
{
logMessage("Error : " + response.message);
alert(response.message);
}
},
error: function(x, e)
{
alert(x.readyState + " "+ x.status +" "+ e.msg);
}
});
Here is my dynamic colModel looks like:
{
"result":"0",
"message":"",
"data":{
"records":18,
"total":1,
"page":"1",
"rows":[ ]
},
"colNames":[
"IP Address/Cidr",
"Name",
"IP Decimal",
"Cidr"
],
"colModel":[
{
"name":"adressCidr",
"width":50,
"sortable":true,
"hidden":false,
"sorttype":"function (cellValue,rowObject) { console.log('sorting by ['+rowObject.ipDecimal+']'); return parseInt(rowObject.ipDecimal,10);}"
},
{
"name":"name",
"width":50,
"sortable":true,
"hidden":false
},
{
"name":"ipDecimal",
"width":50,
"sortable":true,
"hidden":false,
"sorttype":"int"
},
{
"name":"cidr",
"width":0,
"sortable":false,
"hidden":true
}
]
}
ipDecimal is a hidden column but I am displaying it for testing purpose. Requirement is first column 'addressCidr' is a string column but i want to sort it using hidden ipDecimal column. The function neither does show console.log message nor does any sorting properly. However, If i sort by ipDecimal with sorttype as 'int' by clicking on its header, it works fine. Only thing i can think of is the double quote around the sorttype function itself. Please let me know if you see any other issue here, or what is the best way to solve this case. Here is snippet where I build json function:
private JsonObjectBuilder createColumn(JsonBuilderFactory factory,
String name,int width,boolean sortable,boolean hidden,boolean sorttype)
{
JsonObjectBuilder column =this.createColumn(factory, name, width, sortable, hidden);
StringBuilder fnBuilder = new StringBuilder("");
//this is not generic but can easily be made one :(
fnBuilder.append("function (cellValue,rowObject) {");
fnBuilder.append(" console.log('sorting by ['+rowObject.ipDecimal+']');");
fnBuilder.append(" return parseInt(rowObject.ipDecimal,10);");
fnBuilder.append("}");
column.add("sorttype", fnBuilder.toString()); // this works, not sure why above function does not work :(
return column;
}
private JsonObjectBuilder createColumn(JsonBuilderFactory factory,
String name,int width,boolean sortable,boolean hidden)
{
JsonObjectBuilder column;
column = factory.createObjectBuilder();
column.add("name", name);
column.add("width", width);
column.add("sortable", sortable);
column.add("hidden", hidden);
return column;
}
Data I used for testing is:
IpAddressCidr ipDecimal
5.1.0.0/24--83951616
5.1.1.0/24--83951872
5.1.2.0/24--83952128
5.1.3.0/24--83952384
5.1.4.0/24--83952640
5.3.0.0/24--84082688
5.9.2.0/24--84476416
6.0.0.0/24--100663296
6.0.1.0/24--100663552
6.0.2.0/24--100663808
6.0.3.0/24--100664064
6.0.4.0/24--100664320
6.0.5.0/24--100664576
7.1.0.0/24--117506048
7.1.1.0/24--117506304
7.1.2.0/24--117506560
7.1.3.0/24--117506816
198.186.198.0/24--3334129152
But here is that I see
Ip 198.186.198.0 should have appeared at the top as it has highest ipDecimal, but it gets pushed to the bottom.
To add more test information. If I remove enclosed double quotes, sort works fine, but not with it.
Following works:
{ name: "adressCidr", width:50, sortable: true,
sorttype: function (cellValue,rowObject) { console.log('sorting by ['+rowObject.ipDecimal+']');return parseInt(rowObject.ipDecimal,10);}},
Following does not:
{ name: "adressCidr", width:50, sortable: true,
sorttype: "function (cellValue,rowObject) { console.log('sorting by ['+rowObject.ipDecimal+']');return parseInt(rowObject.ipDecimal,10);}"},
The reason of your problem is the usage of sorttype which you defines as string instead of function:
{
"name":"adressCidr",
"width":50,
"sortable":true,
"hidden":false,
"sorttype":"function (cellValue,rowObject) { console.log('sorting by ['+rowObject.ipDecimal+']'); return parseInt(rowObject.ipDecimal,10);}"
}
You use jqGrid 4.7 which contains new feature which I suggested (see here). So you can include the code like
$.extend($.jgrid, {
cmTemplate: {
myIpAddress: {
sorttype: function (cellValue, rowObject) {
console.log('sorting by [' + rowObject.ipDecimal + ']');
return parseInt(rowObject.ipDecimal, 10);
},
width: 50
}
}
});
Now you can change the data returned from the server to
{
"name":"adressCidr",
"sortable":true,
"hidden":false,
"template":"myIpAddress"
}
the jq grid is running fine on asp.net dev server but on IIS 8 (Windows Server 2012) it is giving the following error: Object doesn't support property or method 'jqGrid'
JS
<script type="text/javascript">
jQuery(document).ready(function () {
jQuery('#GridList').jqGrid({
autoencode: true,
autowidth: true,
caption: 'List',
cmTemplate: { sortable: false },
datatype: 'json',
jsonReader: { 'repeatitems': false, 'id': 'Id' },
emptyrecords: 'No record Found',
multiselect: true,
gridview: true,
recordpos: 'left',
height: '100%',
loadui: 'block',
pager: '#pager',
rowList: [10, 15, 20, 50],
rowNum: 10,
viewsortcols: [true, 'vertical', true],
shrinkToFit: true,
url: '#Url.Action("List")',
viewrecords: true,
width: '650',
colModel: [
#Html.GetGridColumn(model => model.Id),
#Html.GetGridColumn(model => model.ResultId),
#Html.GetGridColumn(model => model.HostReference),
#Html.GetGridColumn(model => model.FirstName),
#Html.GetGridColumn(model => model.LastName),
#Html.GetGridColumn(model => model.UserID)
]
});
//jQuery('#GridList').jqGrid('filterToolbar', { stringResult: true, searchOnEnter: false });
jQuery("#GridList").navGrid('#pager', { edit: false, add: false, del: false });
jQuery("#btnSubmit").click(function () {
var s;
s = jQuery("#GridList").jqGrid('getGridParam', 'selarrrow');
alert(s);
});
});
</script>
Update:
this is how i call the list:
protected ActionResult List(GridSettings grid)
{
var query = ListQuery.AsQueryable().OrderBy(grid.SortColumn, grid.SortOrder);
if (grid.IsSearch && grid.Where != null && grid.Where.rules != null)
{
query = grid.Where.rules.Aggregate(query,
(current, rule) => current.Where(rule.field, rule.data, rule.op));
}
var count = query.Count();
var data = query.Skip((grid.PageIndex - 1) * grid.PageSize)
.Take(grid.PageSize)
.Select(Mapper.Map<TModel, TListModel>);
// TO DO: Prevent GridDataType.NoDisplay fields from being
// serialised
var result = new
{
total = (int)Math.Ceiling((double)count / grid.PageSize),
page = grid.PageIndex,
records = count,
rows = data.ToArray()
};
var serialiser = new JavaScriptSerializer();
serialiser.MaxJsonLength = int.MaxValue;
//serialiser.RegisterConverters(new[] { new SingleSelectConverter() });
//serialiser.RegisterConverters(new[] { new MultiSelectConverter() });
var jsonString = serialiser.Serialize(result);
return new ContentResult { Content = jsonString, ContentType = "application/json"};
}
What seems that you have issue of reference, just check the jqgrid library path whether that is referenced properly or not.
or may be you could have forgot to reference the library with all other required library.
some side notes:
Since you are using dataType:"json" and i can see that you have not used loadonce: true option in the list which is required when dataType is "json" and you have mentioned your column names, try including those too.:
jQuery('#GridList').jqGrid({
autoencode: true,
autowidth: true,
caption: 'List',
cmTemplate: { sortable: false },
datatype: 'json',
........
loadonce: true
});
Finally i found my answer, i was using third party dll, it's in dll folder, when i depolyed, i had to add to bin folder as well...Thank you for the help