I created an Eclipse application where I implemented the row selection for the NatTable with a single column header. The row selection works correctly. Later I added a NatTable with a column group header to the application. Here comes problem, after clicking on cell the row selection doesn't work. Only clicked cell is selected.
I define the row selection in RowSelectionAction extends AbstractSelectionAction
class. RowSelectionAction
object is created in overrided configureBodyMouseClickBindings()
method of class extends DefaultSelectionBindings
. This method is called during NatTable.configure()
method. But it seems configureBodyMouseClickBindings()
method isn't called at NatTable created with column groupd headers.
Here is code for creating NatTable with simple column header:
private NatTable createTable(Composite parent, List<TableLine> tLines, String[][] propertyNames,
PropertyToLabels[] propToLabels, TableParams params, TextMatcherEditor<TableLine>editor) {
BodyLayerStack bodyLayerStack =
new BodyLayerStack(
tLines,
new LineDataProviderColumnAccessor(propertyNames[0].length),
params.getColumnIndicesForRowHeaders());
DataLayer bodyDataLayer = bodyLayerStack.getBodyDataLayer();
Integer[] rowHeights = params.getRowHeights();
if( rowHeights != null && rowHeights.length > 0 ) {
for( int i = 0; i < rowHeights.length; i++ ) {
if( rowHeights[i] != null )
bodyDataLayer.setRowHeightByPosition(i, rowHeights[i]);
}
}
Integer[] colWidths = params.getColumnWidths();
if( colWidths != null && colWidths.length > 0 ) {
for( int i = 0; i < colWidths.length; i++ )
if( colWidths[i] != null )
bodyDataLayer.setColumnWidthByPosition(i, colWidths[i]);
}
IDataProvider columnHeaderDataProvider =
new DefaultColumnHeaderDataProvider(propertyNames[0], propToLabels[0].getPropertyToLabels());
DataLayer columnHeaderDataLayer =
new DefaultColumnHeaderDataLayer(columnHeaderDataProvider);
ILayer columnHeaderLayer =
new ColumnHeaderLayer(
columnHeaderDataLayer,
bodyLayerStack,
(SelectionLayer)null);
Integer[] hrHeights = params.getHeaderRowHeights();
if( hrHeights != null && hrHeights.length > 0 )
columnHeaderDataLayer.setRowHeightByPosition(0, hrHeights[0]);
CompositeLayer composite = new CompositeLayer(1, 2);
composite.setChildLayer(GridRegion.COLUMN_HEADER, columnHeaderLayer, 0, 0);
composite.setChildLayer(GridRegion.BODY, bodyLayerStack, 0, 1);
NatTable natTable = new NatTable(parent, composite, false);
natTable.addConfiguration(new DefaultNatTableStyleConfiguration());
natTable.addConfiguration(new ContextMenuConfiguration(natTable));
natTable.addConfiguration(new AbstractRegistryConfiguration() {
@Override
public void configureRegistry(IConfigRegistry configRegistry) {
Style cellStyle = new Style();
cellStyle.setAttributeValue(
CellStyleAttributes.BACKGROUND_COLOR,
GUIHelper.COLOR_WIDGET_BACKGROUND);
configRegistry.registerConfigAttribute(
CellConfigAttributes.CELL_STYLE, cellStyle,
DisplayMode.NORMAL, RowHeaderLabel);
}
});
natTable.configure();
editor.setFilterator(new TextFilterator<TableLine>() {
@Override
public void getFilterStrings(List<String> baseList, TableLine element) {
for( int i = 0; i < element.getLength(); i++ )
baseList.add("" + element.getObjectByColumn(i));
}
});
editor.setMode(TextMatcherEditor.REGULAR_EXPRESSION);
bodyLayerStack.getFilterList().setMatcherEditor(editor);
return natTable;}
BodyLayerStack.class content:
class BodyLayerStack extends AbstractLayerTransform {
private final FilterList<TableLine> filterList;
private final SelectionLayer selectionLayer;
private final DataLayer bodyDataLayer;
private final IRowDataProvider<TableLine> bodyDataProvider;
public DataLayer getBodyDataLayer() {
return bodyDataLayer;
}
public SelectionLayer getSelectionLayer() {
return selectionLayer;
}
public IRowDataProvider<TableLine> getBodyDataProvider() {
return bodyDataProvider;
}
public BodyLayerStack(List<TableLine> values, IColumnAccessor<TableLine> columnAccessor, Integer[] columnIndicesForRowHeaders) {
EventList<TableLine> eventList = GlazedLists.eventList(values);
TransformedList<TableLine, TableLine> rowObjectsGlazedList = GlazedLists.threadSafeList(eventList);
this.filterList = new FilterList<>(rowObjectsGlazedList);
this.bodyDataProvider = new ListDataProvider<TableLine>(this.filterList, columnAccessor);
bodyDataLayer = new DataLayer(this.bodyDataProvider);
ColumnOverrideLabelAccumulator bodyLabelAccumulator = new ColumnOverrideLabelAccumulator(bodyDataLayer);
bodyDataLayer.setConfigLabelAccumulator(bodyLabelAccumulator);
if( columnIndicesForRowHeaders != null ) {
for ( int i = 0; i < columnIndicesForRowHeaders.length; i++ ) {
bodyLabelAccumulator.registerColumnOverrides(
columnIndicesForRowHeaders[i],
RowHeaderLabel);
}
}
GlazedListsEventLayer<TableLine> glazedListsEventLayer =
new GlazedListsEventLayer<>(bodyDataLayer, this.filterList);
this.selectionLayer = new SelectionLayer(glazedListsEventLayer, false);
selectionLayer.setSelectionModel(new RowSelectionModel<TableLine>(selectionLayer, this.bodyDataProvider, new IRowIdAccessor<TableLine>()
{
@Override
public Serializable getRowId(TableLine line)
{
return line.getId();
}
}));
selectionLayer.addConfiguration(new DefaultSelectionLayerConfiguration()
{
@Override
protected void addSelectionUIBindings()
{
addConfiguration(new SelectionBindings());
}
@SuppressWarnings("rawtypes")
@Override
protected void addMoveSelectionConfig()
{
addConfiguration(new RowOnlySelectionConfiguration());
}
});
ViewportLayer viewportLayer = new ViewportLayer(selectionLayer);
setUnderlyingLayer(viewportLayer);
}
public FilterList<TableLine> getFilterList() {
return this.filterList;
}
}
Here is code for creating column group header NatTable:
private NatTable createTableWithColumnHeaderGroups(Composite parent, List<TableLine> tLines, TableParams params,
TextMatcherEditor<TableLine> editor) {
String[][] columnHeaders = params.getColumnHeaders();
if( columnHeaders == null || columnHeaders.length != 2 )
return null;
String[] propertyNames = new String[columnHeaders[1].length];
PropertyToLabels propToLabels = new PropertyToLabels();
for( int i = 0; i < propertyNames.length; i++ ) {
propertyNames[i] = String.valueOf(i+1) + "_" + columnHeaders[1][i];
propToLabels.add(propertyNames[i], columnHeaders[1][i]);
}
BodyLayerStack bodyLayerStack =
new BodyLayerStack(
tLines,
new LineDataProviderColumnAccessor(propertyNames.length),
params.getColumnIndicesForRowHeaders());
ColumnGroupModel columnGroupModel = new ColumnGroupModel();
IRowDataProvider<TableLine> bodyDataProvider =
new ListDataProvider<TableLine>(tLines, new LineDataProviderColumnAccessor(propertyNames.length));
ColumnGroupBodyLayerStack bodyLayer =
new ColumnGroupBodyLayerStack(bodyLayerStack.getBodyDataLayer(), columnGroupModel);
Integer[] rowHeights = params.getRowHeights();
if( rowHeights != null && rowHeights.length > 0 ) {
for( int i = 0; i < rowHeights.length; i++ ) {
if( rowHeights[i] != null )
bodyLayer.doCommand(new RowResizeCommand(bodyLayer, i, rowHeights[i]));
}
}
Integer[] colWidths = params.getColumnWidths();
if( colWidths != null && colWidths.length > 0 ) {
for( int i = 0; i < colWidths.length; i++ )
if( colWidths[i] != null )
bodyLayer.doCommand(new ColumnResizeCommand(bodyLayer, i, colWidths[i]));
}
// Column header
DefaultColumnHeaderDataProvider defaultColumnHeaderDataProvider =
new DefaultColumnHeaderDataProvider(propertyNames, propToLabels.getPropertyToLabels());
DefaultColumnHeaderDataLayer columnHeaderDataLayer =
new DefaultColumnHeaderDataLayer(defaultColumnHeaderDataProvider);
ColumnHeaderLayer columnHeaderLayer =
new ColumnHeaderLayer(columnHeaderDataLayer, bodyLayer, bodyLayer.getSelectionLayer());
ColumnGroupHeaderLayer columnGroupHeaderLayer =
new ColumnGroupHeaderLayer(
columnHeaderLayer,
bodyLayer.getSelectionLayer(),
columnGroupModel);
Integer[] hrHeights = params.getHeaderRowHeights();
if( hrHeights != null && hrHeights.length > 0 )
for( int i = 0; i < hrHeights.length; i++ )
if( hrHeights[i] != null )
columnGroupHeaderLayer.doCommand(new RowResizeCommand(columnGroupHeaderLayer, i, hrHeights[i]));
List<ColumnHeaderGroup> groups = params.getColumnHeaderGroups();
for( ColumnHeaderGroup group : groups ) {
List<Integer> indices = group.getIndices();
int[] indicesArray = new int[indices.size()];
for( int i = 0; i < indices.size(); i++ )
indicesArray[i] = indices.get(i);
columnGroupHeaderLayer.addColumnsIndexesToGroup(group.getName(), indicesArray);
}
// Row header
final DefaultRowHeaderDataProvider rowHeaderDataProvider =
new DefaultRowHeaderDataProvider(bodyDataProvider);
DefaultRowHeaderDataLayer rowHeaderDataLayer =
new DefaultRowHeaderDataLayer(rowHeaderDataProvider);
ILayer rowHeaderLayer =
new RowHeaderLayer(rowHeaderDataLayer, bodyLayer, bodyLayer.getSelectionLayer());
// Corner
final DefaultCornerDataProvider cornerDataProvider =
new DefaultCornerDataProvider(defaultColumnHeaderDataProvider, rowHeaderDataProvider);
DataLayer cornerDataLayer =
new DataLayer(cornerDataProvider);
ILayer cornerLayer =
new CornerLayer(cornerDataLayer, rowHeaderLayer, columnGroupHeaderLayer);
// Grid
GridLayer gridLayer =
new GridLayer(bodyLayer, columnGroupHeaderLayer, rowHeaderLayer, cornerLayer);
NatTable natTable = new NatTable(parent, gridLayer, false);
editor.setFilterator(new TextFilterator<TableLine>() {
@Override
public void getFilterStrings(List<String> baseList, TableLine element) {
for( int i = 0; i < element.getLength(); i++ )
baseList.add("" + element.getObjectByColumn(i));
}
});
editor.setMode(TextMatcherEditor.REGULAR_EXPRESSION);
bodyLayerStack.getFilterList().setMatcherEditor(editor);
natTable.addConfiguration(new DefaultNatTableStyleConfiguration());
natTable.addConfiguration(new ContextMenuConfiguration(natTable));
natTable.addConfiguration(new AbstractRegistryConfiguration() {
@Override
public void configureRegistry(IConfigRegistry configRegistry) {
Style cellStyle = new Style();
cellStyle.setAttributeValue(
CellStyleAttributes.BACKGROUND_COLOR,
GUIHelper.COLOR_WIDGET_BACKGROUND);
configRegistry.registerConfigAttribute(
CellConfigAttributes.CELL_STYLE, cellStyle,
DisplayMode.NORMAL, RowHeaderLabel);
}
});
natTable.configure();
return natTable; }
Eventually, the problem may be in nat table layer implementation at nat table with two-row column headers creation.
See Question&Answers more detail:
os