应该使用beforeProcessing 而不是loadComplete 对从服务器加载的数据进行一些修改。该回调在loadonce: true场景下非常实用,因为它只会在从服务器加载数据后调用一次。
理解应该尽量减少 HTML 页面的 DOM 上的更改次数,这一点非常重要。如果您在 HTML 解析器处理之前更改数据,那么它会非常快速地工作:您更改一个属性,并且只会更改该属性。另一方面,更改 HTML 页面上的一个元素会遵循重新计算,并且可能会更改页面上存在的 all 其他元素。例如,您在网格上插入一个元素。然后网格的位置(以及网格的所有其他元素)将发生变化。至少网络浏览器必须验证是否需要对 all 现有元素进行某些更改。这是browser reflow。如果您在循环中更改 HTML 元素(例如在 loadComplete 中调用 setRowData),那么它实际上会降低 HTML 页面的速度。
再说一句。我建议您使用 JSFiddle 的 Echo 服务(请参阅here)来模拟从服务器加载数据。对应的代码如下:
var i, data = [], grid = $('#grid');
for(i=0; i<4; i++) {
data.push({id:i, select1: i%3});
}
grid.jqGrid({
datatype: "json",
mtype: "POST",
url: "/echo/json/",
postData: {
json: JSON.stringify(data)
},
loadonce: true,
forceClientSorting: true,
caption: 'Testing',
editurl: 'clientArray',
rowNum: 2,
rowList: [2, 4],
pager: true,
colModel: [
{name:'select1', label: 'Server status', editable:true, edittype:'select', formatter:'select', template: "integer", editoptions:{
value:'0:AAA;1:BBB;2:CCC'
}},
{name:'select2', label: 'Local status', editable: true, edittype: 'select', formatter:'select', editoptions:{
value:'0:AAA;1:BBB;2:CCC'
}},
{name:'act', template:'actions'}
],
inlineEditing: {
keys: true
},
beforeProcessing: function(data){
var i;
for(i=0; i<data.length; i++){
data[i].select2 = 0;
}
}
});
$('#b1').click(function(){
$('#out').empty()
var i, gridData = grid.jqGrid('getGridParam','data');
for(i=0; i<gridData.length; i++){
out(JSON.stringify(gridData[i]));
}
});
function out(message){
$('#out').append('<p>' + message +'</p>');
}
查看修改后的演示 https://jsfiddle.net/OlegKi/c09fnaca/8/。我在第一列中添加了template: "integer",只是为了演示将数据转换为数字。免费 jqGrid 支持convertOnSave 回调(请参阅the wiki article),这有助于在保存本地数据期间进行某种类型的转换。例如定义如下回调(见the lines的代码)
convertOnSave: function (options) {
var nData = options.newValue;
return isNaN(nData) ? nData : parseInt(nData, 10);
}
因此,第一列中使用的数据将被转换为数字,而不是将数据保存为字符串。