Sha*_*awn 6 javascript jquery jqgrid
我目前正在使用afterSaveCell
手动更新网格中的某些单元格.如果用户使用enter保存当前编辑的单元格,我可以正常工作.
不幸的是,如果他们点击或跳出单元格,他们正在直接编辑到另一个单元格,我不能再抓取新编辑的单元格的单元格值,因为getCell
只返回输入控件的html.
总之,即使在编辑单元格时,有没有办法访问单元格的值?
jQuery(document).ready(function () {
var mydata = [
{id:"1", invdate:"2007-10-01",name:"test", note:"note", amount:"200.00",tax:"10.00",total:"210.00"},
{id:"2", invdate:"2007-10-02",name:"test2", note:"note2", amount:"300.00",tax:"20.00",total:"320.00"},
{id:"3", invdate:"2007-09-01",name:"test3", note:"note3", amount:"400.00",tax:"30.00",total:"430.00"},
{id:"4", invdate:"2007-10-04",name:"test", note:"note4", amount:"200.00",tax:"10.00",total:"210.00"},
{id:"5", invdate:"2007-10-05",name:"test5", note:"note5", amount:"300.00",tax:"20.00",total:"320.00"},
{id:"6", invdate:"2007-09-06",name:"test", note:"note6", amount:"400.00",tax:"30.00",total:"430.00"},
{id:"7", invdate:"2007-10-04",name:"test7", note:"note7", amount:"200.00",tax:"10.00",total:"210.00"},
{id:"8", invdate:"2007-10-03",name:"test8", note:"note8", amount:"300.00",tax:"20.00",total:"320.00"},
{id:"9", invdate:"2007-09-01",name:"test", note:"note9", amount:"400.00",tax:"30.00",total:"430.00"},
{id:"10",invdate:"2007-09-08",name:"test10",note:"note10",amount:"500.00",tax:"30.00",total:"530.00"},
{id:"11",invdate:"2007-09-08",name:"test11",note:"note11",amount:"500.00",tax:"30.00",total:"530.00"},
{id:"12",invdate:"",name:"TOTAL", note:"",amount:"",tax:"",total:""}
];
var grid = $("#list");
grid.jqGrid({
cellsubmit: 'remote',
cellurl: '/Example/GridSave',
datatype: "local",
data: mydata,
mtype: 'POST',
colNames: ['Inv No', 'Date', 'Client', 'Amount', 'Tax', 'Total', 'Notes'],
colModel: [
{ name: 'id', index: 'id', width: 65, sorttype: 'int', hidden: true },
{ name: 'invdate', index: 'invdate', width: 120, align: 'center', formatter: 'date', formatoptions: { newformat: 'd-M-Y' }, sortable: false },
{ name: 'name', index: 'name', editable: true, width: 90, sortable: false },
{ name: 'amount', index: 'amount', editable: true, width: 70, formatter: 'number', align: 'right', sortable: false },
{ name: 'tax', index: 'tax', editable: true, width: 60, formatter: 'number', align: 'right', sortable: false },
{ name: 'total', index: 'total', editable: true, width: 60, formatter: 'number', align: 'right', sortable: false },
{ name: 'note', index: 'note', width: 100, sortable: false }
],
rowNum: 1000,
pager: '#pager',
viewrecords: true,
sortorder: "desc",
caption: "afterSaveCell Issue",
height: "100%",
cellEdit: true,
gridComplete: function () {
calculateTotal();
},
afterSaveCell: function (rowid, name, val, iRow, iCol) {
calculateTotal();
}
});
});
function calculateTotal() {
var totalAmount = 0;
var totalTax = 0;
var grid = jQuery("#list");
var ids = grid.jqGrid('getDataIDs');
for (var i = 0; i < ids.length; i++) {
var id = ids[i];
if (grid.jqGrid('getCell', id, 'name') === "TOTAL") {
grid.jqGrid('setRowData', id, {
'amount': totalAmount,
'tax': totalTax,
'total': totalAmount + totalTax
});
}
else {
totalAmount += Number(grid.jqGrid('getCell', id, 'amount'));
totalTax += Number(grid.jqGrid('getCell', id, 'tax'));
}
}
}
Run Code Online (Sandbox Code Playgroud)
提前致谢!
Ole*_*leg 11
我在你的代码中看到了两个问题.第一个是更美观,但正确的解决方案可以简化未来的许多事情.
第一个问题是您将"TOTAL"行手动添加为网格数据的一部分,并计算calculateTotal
函数内部行中的值.更好的方法是使用footerrow:true
选项,它在网格底部添加额外的行,不会与网格数据混合.对于基于服务器的数据,您可以使用userdata
来自服务器的部分JSON或XML响应,并userDataOnFooter:true
另外使用以将数据从userData
jqGrid参数添加到页脚行.在"本地"数据类型的情况下,可以使用footerData方法设置(或获取)页脚中的数据.另外,可以使用方法getCol来计算列中元素的总和.因此,您的calculateTotal
函数版本可以重写为
var grid = $("#list");
var calculateTotal = function() {
var totalAmount = grid.jqGrid('getCol','amount',false,'sum'),
totalTax = grid.jqGrid('getCol','tax',false,'sum');
grid.jqGrid('footerData','set',{name:'TOTAL',amount:totalAmount,tax:totalTax});
}
Run Code Online (Sandbox Code Playgroud)
现在来看你的主要问题.您使用单元格编辑模式.如果在calculateTotal
'amount'或'tax'的单元格中的一个处于编辑模式时将调用该函数(您的原始版本或我的简化版本),则将calculateTotal
使用<input>
元素而不是带有元素的字符串读取HTML片段数字和计算将失败.
我创建了calculateTotal
每秒调用一次的小型演示.因此,如果您点击"金额"或"税"列中的任何单元格,您会看到页脚行0将显示为总和.因此,演示具有cellsubmit:'clientArray'
与原始代码中相同的问题cellsubmit:'remote'
.
要解决这个问题,可以data
在求和过程中使用jqGrid的参数:
var grid = $("#list");
var calculateTotal = function() {
var gridData = grid.jqGrid('getGridParam','data'),
i=0,totalAmount=0,totalTax=0;
for (;i<gridData.length;i++) {
var rowData = gridData[i];
totalAmount += Number(rowData.amount);
totalTax += Number(rowData.tax);
}
grid.jqGrid('footerData','set',{name:'TOTAL',amount:totalAmount,tax:totalTax});
}
Run Code Online (Sandbox Code Playgroud)
你会在这里找到相应的固定演示.在您的最终代码中,您可以删除
setInterval(calculateTotal, 1000);
Run Code Online (Sandbox Code Playgroud)
我仅用于演示目的,仅刷新afterSaveCell
事件处理程序中的页脚.
更新:如果使用远程数据,则无法使用data
参数.因此,<input>
如果需要,必须从元素中获取数据.我创建了另一个演示,演示了如何做到这一点.代码calculateTotal
将更长:
var getColumnIndexByName = function(grid,columnName) {
var cm = grid.jqGrid('getGridParam','colModel');
for (var i=0,l=cm.length; i<l; i++) {
if (cm[i].name===columnName) {
return i; // return the index
}
}
return -1;
},
getTextFromCell = function(cellNode) {
return cellNode.childNodes[0].nodeName === "INPUT"?
cellNode.childNodes[0].value:
cellNode.textContent || cellNode.innerText;
},
calculateTotal = function() {
var totalAmount = 0, totalTax = 0,
i=getColumnIndexByName(grid,'amount');
$("tbody > tr.jqgrow > td:nth-child("+(i+1)+")",grid[0]).each(function() {
totalAmount += Number(getTextFromCell(this));
});
i=getColumnIndexByName(grid,'tax');
$("tbody > tr.jqgrow > td:nth-child("+(i+1)+")",grid[0]).each(function() {
totalTax += Number(getTextFromCell(this));
});
grid.jqGrid('footerData','set',{name:'TOTAL',amount:totalAmount,tax:totalTax});
};
Run Code Online (Sandbox Code Playgroud)