I modified the code of Oleg to be able to show the grouping in the first row, basically I created a dummy third row and just deleted the text in the first row.
var x = 0;
insertColumnGroupHeader = function (mygrid, mergeSettingList) {
var i, cmi, skip = 0, $tr, colHeader, iCol, $th,
colModel = mygrid[0].p.colModel,
ths = mygrid[0].grid.headers,
gview = mygrid.closest("div.ui-jqgrid-view"),
thead = gview.find("table.ui-jqgrid-htable>thead");
$tr = $("<tr>");
var currCaption = '';
var currColumnName = '';
var currSpan = 0;
var currSkip = 0;
tr = "<tr>";
for (i = 0; i < colModel.length; i++) {
$th = $(ths[i].el);
cmi = colModel[i];
if (currSkip === 0) {
currColumnName = '';
for (j = 0; j < mergeSettingList.length; j++) {
if (mergeSettingList[j].col == cmi.name) {
currCaption = mergeSettingList[j].caption;
currColumnName = mergeSettingList[j].col;
currSpan = mergeSettingList[j].span;
currWidth = mergeSettingList[j].width;
break;
}
}
}
if (cmi.name !== currColumnName) {
if (currSkip === 0) {
$th.attr("rowspan", "2");
} else {
// Skip part of group
denySelectionOnDoubleClick($th);
currSkip--;
}
} else {
denySelectionOnDoubleClick($th);
tr += '<th class="ui-state-default ui-th-ltr" colspan="' + currSpan + '" role="columnheader">' + currCaption + '</th>';
currSkip = currSpan - 1;
}
}
tr += "</tr>";
mygrid.closest("div.ui-jqgrid-view").find("table.ui-jqgrid-htable > thead").append(tr);
$th = $(ths[0].el);
tr = "<tr>";
var html = $th.parent().html();
tr += html;
tr += "</tr>";
mygrid.closest("div.ui-jqgrid-view").find("table.ui-jqgrid-htable > thead").append(tr);
for (i = 0; i < colModel.length; i++) {
$th = $(ths[i].el);
cmi = colModel[i];
$th.empty();
$th.css({"padding-top": "0px", height: "0px", border: "0px"});
}
}
Sample call.
var mergeParam = [
{caption: ' ', col: 'ActionKey', span: 3},
{caption: 'Planned', col: 'PlannedStartColKey', span: 5},
{caption: 'Actual', col: 'ActualStartColKey', span: 12}
];
insertColumnGroupHeader2($(GridNames.Grid), mergeParam);