I have extjs grid.Panel and I am trying to mimic cell merging in the rows when there is duplicate data in the first column of consecutive rows. Using a column renderer, I clear a row's first column value if it is a duplicate of a previous row's value. I would like to modify the previous row's first cell's tdAttr to row span the appropriate number of rows. I cannot figure out how to get to a previous row's metaData. Below is my current renderer code.
renderer: function(value, metaData, record, row, col, store, gridView){
var dataIndex = metaData.column.dataIndex;
var overrideValue = value;
// check previous rows and determine whether this row's first column has the same
// value as a previous row's first column
if (col == 0){
var i = row-1;
while (i >= 0 && overrideValue != ""){
if (store.data.items[i].get(dataIndex) == value){
overrideValue = "";
// ----- here i want to update record i's metaData...
// metaData.tdAttr = 'rowspan=' + row-i+1
}
i--;
}
}
return overrideValue;
}
I've tried a number of ways to get at the metaData associated with a record but have been unsuccessful. The getnodes and getnode methods of the gridView object return undefined.
I created the following solution. I used a combination of a column renderer and a view listener, specifically "viewready". The grid's row line is set to "false" and I use the column renderer to apply a custom style to replace the row line as appropriate and clear the appropriate cells values. I modify the background color of "merged" cells in the "viewready" listener.
<style>
.mywrapcell .x-grid-cell-inner {
white-space: normal;
border-top-color: #c6c6c6;
border-top-width: 1px;
border-top-style: solid;
}
</style>
_addGrid: function() {
var myModel = Ext.define('User', {
extend: 'Ext.data.Model',
fields: [
{name: 'col1', type: 'string'},
{name: 'col2', type: 'string'},
]
});
var myData = [{col1: 'U2', col2: 'Jan 5'},
{col1: 'U2', col2: 'Jan 6'},
{col1: 'Crowded House', col2: 'Feb 19'},
{col1: 'Jack Johnson', col2: 'Apr 4'},
{col1: 'Jack Johnson', col2: 'Apr 5'},
{col1: 'Cage the Elephant', col2: 'May 10'},
{col1: 'Cage the Elephant', col2: 'May 11'},
{col1: 'Blondie', col2: 'Jun 6'},
{col1: 'Gorillaz', col2: 'Jun 19'},
{col1: 'Gorillaz', col2: 'Jun 20'}];
var mystore = Ext.create('Ext.data.Store', {
model: myModel,
data: myData,
proxy: {
type: 'memory',
enablePaging: false
}
});
var mygrid = Ext.create('Ext.grid.Panel', {
store: mystore,
itemId: 'grid',
viewConfig:{
listeners: {
viewready: function(view){
var dataIndex = 'col1';
// find the index of the column for row spanning
var colindex = view.ownerCt.columns.findIndex((x) => x.dataIndex == dataIndex);
if (colindex != -1){
var viewrows = view.getNodes();
var bgcolor = '#fff';
// set all the cells to the
// same background color
for(i=0;i<viewrows.length;i++){
viewrows[i].cells[colindex].style.backgroundColor = bgcolor;
}
}
}
},
enableEditing: false,
enableBulkEdit: false,
showRowActionsColumn: false,
enableRanking: false,
sortableColumns: false,
columnLines: true,
rowLines: false, //row lines handled in renderer
width: 225,
columns: [
{text: 'Artist',
dataIndex: 'col1',
flex: 1,
renderer: function(value, metaData, record, row, col, store, view){
var overrideValue = value;
// check previous rows and determine whether this row's first column has the same
// value as a previous row's first column
var i = row-1;
while (i >= 0 && overrideValue != ""){
if (store.data.items[i].get(metaData.column.dataIndex) == value){
overrideValue = '';
}
i--;
}
if (overrideValue != ""){
metaData.tdCls = 'mywrapcell';
}
return overrideValue;
}
},
{
text: 'Show Date',
dataIndex: 'col2',
tdCls: 'mywrapcell'
}
],
});
this.add(mygrid);
}