所以我浪费了一整天跟踪数据,但无法找到解决方案,所以发布在这里。 以下是我的 js 代码。
<script type="text/javascript">
jq(function() {
jq("#Grid").jqGrid({
url:'/indyaah/crud.htm',
datatype: 'json',
mtype: 'GET',
colNames:['User Id','User Name','Book Id','Book Name'],
colModel:[
{name:'userId',index:'userId', formatter: 'select', stype: 'select',edittype: 'select',editoptions:{value:Users()},editable:true, editrules:{required:true,edithidden:true},searchoptions:{sopt: ['eq','ne','le','ge']},hidden:true},
{name:'userName',index:'userName', width:100,editable:false},
{name:'bookId',index:'bookId', formatter: 'select', stype: 'select',edittype: 'select',editoptions:{value:Books()},editable:true, editrules:{required:true,edithidden:true},searchoptions:{sopt: ['eq','ne','le','ge']},hidden:true},
{name:'BookName',index:'BookName', width:100},
],
postData: {
},
rowNum:5,
altRows:true,
hiddengrid:true,
rowList:[5,10],
height: "100%",
autowidth: true,
rownumbers: true,
pager: '#pager',
sortname: 'userId',
viewrecords: true,
sortorder: "asc",
caption:"Details",
emptyrecords: "Empty records",
loadonce: false,
autowidth:true,
loadComplete: function() {
},
jsonReader : {
root: "rows",
page: "page",
total: "total",
records: "records",
repeatitems: false,
cell: "cell",
id: "id"
}
});
function Users()
{
jq.getJSON('/indyaah/readUsers.htm', function(data) {
var len = data.rows.length;
for ( var i = 0; i < len; i++) {
if(i===0) html += '' + data.rows[i].userId + ' : \'' + data.rows[i].userName + '\',' ;
else if(i===len-1) html += data.rows[i].userId + ' : \'' + data.rows[i].userName + '\'' ;
else html += data.rows[i].userId + ' : \'' + data.rows[i].userName + '\',' ;
}
});
return html;
}
function Books()
{
jq.getJSON('/indyaah/readBooks.htm', function(data) {
var len = data.rows.length;
for ( var i = 0; i < len; i++) {
if(i===0) html += '{\'' + data.rows[i].bookId + '\':\'' + data.rows[i].name + '\',\n' ;
else if(i===len-1) html += '\''+ data.rows[i].bookId + '\':\'' + data.rows[i].name + '\'}' ;
else html += '\''+ data.rows[i].bookId + '\':\'' + data.rows[i].name + '\',\n' ;
}
});
return html;
}
jq("#Grid").jqGrid('navGrid','#pager',
{edit:false,add:false,del:false,search:true},
{ },
{ },
{ },
{
sopt:['eq', 'ne', 'le', 'ge', 'cn', 'bw', 'ew'],
closeOnEscape: true,
multipleSearch: true,
closeAfterSearch: true },
{width:500}
);
jq("#Grid").navButtonAdd('#pager',
{ caption:"Add",
buttonicon:"ui-icon-plus",
onClickButton: add,
position: "last",
title:"",
cursor: "pointer"
}
);
jq("#Grid").navButtonAdd('#pager',
{ caption:"Edit",
buttonicon:"ui-icon-pencil",
onClickButton: edit,
position: "last",
title:"",
cursor: "pointer"
}
);
jq("#Grid").navButtonAdd('#pager',
{ caption:"Delete",
buttonicon:"ui-icon-trash",
onClickButton: delete,
position: "last",
title:"",
cursor: "pointer"
}
);
jq("#btnFilter").click(function(){
jq("#Grid").jqGrid('searchGrid',
{multipleSearch: true,
sopt:['eq']}
);
});
jq("#Grid").jqGrid('filterToolbar',{stringResult: true,searchOnEnter : true, defaultSearch:"cn"});
});
</script>
两个Jsons都有以下格式(我只显示了3-4列,但分别有8和10),
{
page: 1
records: 5
rows: [
0: {displayName:ABC, password:null, userName:123, userId:1,…}
1: {displayName:DEF, password:null, userName:456, userId:2,…}
2: {displayName:GHI, password:null, userName:789, userId:3,…}
3: {displayName:JKL, password:null, userName:234, userId:4,…}
4: {displayName:MNO, password:null, userName:548, userId:5,…}
5: {displayName:PQR, password:null, userName:968, userId:6,…}
]
}
和
{
page: 1
records: 5
rows: [
0: {displayName:ABC, bookName:123, bookId:1,…}
1: {displayName:DEF, bookName:456, bookId:2,…}
2: {displayName:GHI, bookName:789, bookId:3,…}
3: {displayName:JKL, bookName:234, bookId:4,…}
4: {displayName:MNO, bookName:548, bookId:5,…}
5: {displayName:PQR, bookName:968, bookId:6,…}
]
}
我的编辑/添加表单看起来像 请注意,在编辑/添加中,我只使用服务器在Json中发送的一些值。!
所以基本上问题是网格加载完美但是一旦我尝试添加或编辑, 选择框为空。 当我在firebug中调试时,Controller会发送数据,但它没有加载到网格中。
那么,我在这里失踪了什么?
答案 0 :(得分:4)
问题的原因很明显,但解决方案并不容易,因为jqGrid并不真正支持从服务器加载formatter: 'select'
和editoptions.value
的使用。我试着描述问题的根源并描述解决方法。
第一个问题是$.getJSON
工作异步。因此,如果将调用Users()
或Books()
,则将从函数返回undefined
值。顺便说一下,html
变量在代码中确实是未定义的。
我可以建议一些解决当前问题的方法。
您只需从列定义中删除edittype: 'select', editoptions: {value: Users()}, editable: true
和edittype: 'select' ,editoptions: {value: Books()}, editable: true
即可。您可以在相应的success
来电的$.getJSON
处理程序中设置设置:
jq("#Grid").jqGrid({
...
});
jq.getJSON('/indyaah/readUsers.htm', function (data) {
var len = data.rows.length, i, html = '', item;
for (i = 0; i < len; i++) {
item = data.rows[i];
if (i !== 0) {
html += ',';
}
html += item.userId + ":'" + item.userName + "'";
}
jq("#Grid").jqGrid('setColProp', 'userId', {
edittype: 'select',
editoptions: {value: html},
editable: true
});
});
jq.getJSON('/indyaah/readBooks.htm', function (data) {
...
jq("#Grid").jqGrid('setColProp', 'bookId', {
edittype: 'select',
editoptions: {value: html},
editable: true
});
});
在打开“添加”或“编辑”表单时,editoptions.value
的正确值已经在colModel
中,并且应该正确显示选择。
在填充网格主体之前,您仍然需要使用formatter: 'select'
来填充需要editoptions.value
的问题。你写道网格填充正确。我认为这意味着对'/indyaah/readUsers.htm'和'/indyaah/readBooks.htm'的请求由服务器''/ indyaah / crud.htm'回答。我发现它很危险。
所以我建议你在jqGrid中使用第一个datatype: 'local'
选项。它将阻止网格加载。您应该设置datatype: 'json'
并在之后调用jq("#Grid").trigger("reloadGrid")
,colModel
的所有选择(两个选择)都已加载。相应的实现很容易。例如:
var filledSelects = 0,
$grid = jq("#Grid");
fillSelectWithData = function (data, colName, idProp, nameProp) {
var len = data.rows.length, i, html = '', item;
for (i = 0; i < len; i++) {
item = data.rows[i];
if (i !== 0) {
html += ',';
}
html += item[idProp] + ":'" + item[nameProp] + "'";
}
$grid.jqGrid('setColProp', colName, {
edittype: 'select',
editoptions: {value: html},
editable: true
});
},
loadGridIfRequired = function () {
filledSelects++;
if (filledSelects > 1) {
$grid.jqGrid('setGridParam', {
datatype: 'json'
}).trigger('reloadGrid');
}
};
$grid.jqGrid({
url:'/indyaah/crud.htm',
datatype: 'local'
...
});
jq.getJSON('/indyaah/readUsers.htm', function (data) {
fillSelectWithData(data, 'userId', 'userId', 'userName');
loadGridIfRequired();
});
jq.ajax('/indyaah/readBooks.htm', function (data) {
fillSelectWithData(data, 'bookId', 'bookId', 'user');
loadGridIfRequired();
});
以上所有代码都未经过测试,但我希望它能够正常运行(可能是在修复小错误之后)。