Hi,
I’ve been using the data grid. I recently changed it to allow the user to select multiple records and edit them at the same time. Everything works perfectly if you select multiple rows on the grid using the shift key. I select multiple rows, click edit, enter the new value, and click save, and then click apply and all the records get sent to the servlet to save.
However, when I select multiple records using the grid.selectAll() method and click the apply button DHTMLX throws the following error:
TypeError: Unable to get property 'idd' of undefined or null reference
at a._getRowData (http://localhost:8080/codebase/dhtmlx.js:9:848183)
at dataProcessor.prototype._getAllData (http://localhost:8080/codebase/dhtmlx.js:9:1379468)
at dataProcessor.prototype.sendAllData (http://localhost:8080/codebase/dhtmlx.js:9:1378971)
at dataProcessor.prototype.sendData (http://localhost:8080/codebase/dhtmlx.js:9:1375924)
at Anonymous function (http://localhost:8080/test/selectAllTest.html:121:21)
at a.callEvent (http://localhost:8080/codebase/dhtmlx.js:9:19579)
at _doOnMouseUp (http://localhost:8080/codebase/dhtmlx.js:9:438499)
On debugging, I found it looks like an extra entry with a null row id is added to the array of updated fields. This only happens in IE11, in Chrome it works fine. I was using DHTMLX 4.3, but upgraded to 5.1.0 hoping it would fix the problem.
Here’s my code:
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge"/>
<title>Test Grid</title>
<script type="text/javascript" src="../codebase/dhtmlx.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<link rel="STYLESHEET" type="text/css" href="../codebase/dhtmlx.css">
<link rel="STYLESHEET" type="text/css" href="../shared/dhxScreens.css">
<script type="text/javascript">
dhtmlx.image_path = "../codebase/imgs/";
var test = {};
function handleBodyLoad() {
var data={
rows:[
{ id:1001, data:["valueA_1","valueB_1"] },
{ id:1002, data:["valueA_2","valueB_2"] },
{ id:1003, data:["valueA_3","valueB_3"] }
]
};
test.layout = new dhtmlXLayoutObject(document.body,"1C");
test.layout.cells("a").setText("Test Grid");
test.rfGrid = test.layout.cells("a").attachGrid();
var labels = ["ColumnA", "ColumnB"];
var filters = ["#text_filter", "#text_filter"];
var ids = ["columnA", "columnB"];
var widths = ["100", "150"];
var aligns = ["left", "left"];
var types = ["ro", "ed"];
var sorting = ["str", "str"];
test.rfGrid.setHeader(labels.join(','));
test.rfGrid.attachHeader(filters.join(','));
test.rfGrid.setColumnIds(ids.join(','));
test.rfGrid.setInitWidths(widths.join(','));
test.rfGrid.setColAlign( aligns.join(','));
test.rfGrid.setColTypes(types.join(','));
test.rfGrid.setColSorting(sorting.join(','));
test.rfGrid.setEditable(true);
test.rfGrid.enableMultiselect(true);
test.rfGrid.init();
test.rfGrid.parse(data, "json");
test.dp = new dataProcessor("servlet");
test.dp.setTransactionMode("POST", true);
test.dp.setUpdateMode("off", true); // auto update
test.dp.defineAction("updated",function(response){ return dpRowSavedAction(response,8); });
test.dp.defineAction("inserted",function(response){ return dpRowSavedAction(response,8); });
test.dp.defineAction("deleted",function(response){ return dpRowSavedAction(response,8); });
test.dp.defineAction("invalid",function(response){ return dpSaveFailedAction(response); });
test.dp.defineAction("error",function(response){ return dpSaveFailedAction(response); });
test.dp.init(test.rfGrid);
var formData = [
{type:"fieldset", offsetTop:0, /*width:253,*/ list:[
{type:"input", name: "columnB", label: "Column B", offsetTop:7,required:true,labelWidth:150, inputWidth: 650},
{type:"button", name:"save", value:"Submit", offsetTop:18}
]}
];
buildControls(formData,875,310);
}
function buildControls(formData,dialogWidth,dialogHeight) {
// Creates edit, history, deletion windows and toolbar
var wins = new dhtmlXWindows();
test.editWin = wins.createWindow("Edit", 20, 30, dialogWidth, dialogHeight);
test.editForm = test.editWin.attachForm(formData);
test.editWin.hide();
test.editForm.bind(test.rfGrid);
test.editForm.attachEvent("onButtonClick", function (id) {
console.log("form id = " + id);
// Form save (Add or Edit)
if (test.editForm.validate()) {
var ids = test.rfGrid.getSelectedRowId();
var newVal = test.editForm.getItemValue("columnB");
console.log("setting field " + "columnB" + " to " + newVal);
if (ids){
ids = ids.split(",");
ids.forEach(function(rowId) {
test.rfGrid.cells(rowId, 1).setValue(newVal);
test.rfGrid.cells(rowId, 1).cell.wasChanged=true;
test.dp.setUpdated(rowId, true);
});
}
test.editForm.save();
test.editWin.hide();
test.editWin.setModal(false);
test.editWin.detachEvent(test.editWinCloseHandler);
}
return true;
});
var toolbar = test.layout.attachToolbar();
toolbar.setIconsPath(dhtmlx.image_path);
toolbar.loadStruct("testToolbar.xml");
toolbar.attachEvent("onClick", function(id) {
if(id === 'editRow') {
if(test.rfGrid.getSelectedRowId()) {
test.editWin.setText("Edit");
test.editWin.mode="edit";
test.editWin.setModal(true);
test.editWin.show();
test.editWinCloseHandler = test.editWin.attachEvent("onClose", function(id){
// This is a cancel close
test.editWin.hide();
test.editWin.setModal(false);
test.editWin.detachEvent(test.editWinCloseHandler);
return false;
});
} else {
alert('Please select a row to edit');
}
} else if(id === 'applyChanges') {
test.dp.sendData();
} else if (id === 'selectAll') {
test.rfGrid.selectAll();
}
});
}
</script>
</head>
<body onload="handleBodyLoad()">
</body>
</html>
testToobar.xml:
<?xml version="1.0"?>
<toolbar>
<item id="editRow" type="button" text="Edit"/>
<item id="applyChanges" type="button" text="Apply"/>
<item id="sep1" type="separator"/>
<item id="selectAll" type="button" text="Select All"/>
</toolbar>