javasortinggwtuibindercelltable

GWT - CellTable sortable column won't respond to clicks


I have a GWT Celltable column that needs to be sorted alphabetically. I followed the official documentation and other questions posted here, but I have not been able to get it to work.

I want the column to sort both ascending and descending. Currently, the carat symbol shows up next to the column header but nothing happens when it is clicked. There are no errors being thrown in the browser console either.

What am I doing wrong? My obfuscated code -

public class MyClass extends Composite {
    //other fields
    private static MyUiBinder uiBinder = GWT.create(MyUiBinder.class);
    @UiField CellTable<MyObject> myTable = new CellTable<MyObject>();
    final ListDataProvider<MyObject> myDataProvider = new ListDataProvider<MyObject>();

    @UiConstructor
    public MyClass(...) {
        initWidget(uiBinder.createAndBindUi(this));
        // other initialization
        buildMyTable();
    }

    buildMyTable() {
        myDataProvider.addDataDisplay(myTable);

        Column<MyObject, String> colA = new Column<MyObject, String>(new TextCell()) {

            @Override
            public String getValue(MyObject object) {
                return object.getName();
            }
        };

        Column<MyObject, String> colB = new Column<MyObject, String>(new TextCell()) {

            @Override
            public String getValue(MyObject object) {
                return object.getAddress();
            }
        };

        // created other columns

        colA.setSortable(true);

        myTable.addColumn(colA, "COL A");
        myTable.addColumn(colB, "COL B");
        // added other columns to the table

        ListHandler<MyObject> columnSortHandler = new ListHandler<>(myDataProvider.getList());
        columnSortHandler.setComparator(colA, new Comparator<MyObject>() {

            @Override
            public int compare(MyObject o1, MyObject o2) {
                if (o1 == o2) {
                    return 0;
                }

                if (o1 != null) {
                    return (o2 != null) ? o1.getName.compareTo(o2.getName) : 1;
                }
                return -1;
            }
        });

        myTable.addColumnSortHandler(columnSortHandler);
        myTable.getColumnSortList().push(colA);
        ColumnSortEvent.fire(myTable, myTable.getColumnSortList());
    }
}

Solution

  • It is all about how do you add data to the CellTable. For example, you can

    myDataProvider.setList(rowData);
    

    or

    myTable.setRowData(rowData);
    

    but both above methods will not allow the data to be sorted. That is because, you already have ListHandler defined with an empty list. And it will not notice that the list have changed, so no sorting will be performed.

    See ListDataProvider documentation:

    Modifications (inserts, removes, sets, etc.) to the list returned by getList() will be reflected in the model. However, mutations to the items contained within the list will NOT be reflected in the model. You must call List.set(int, Object) to update the item within the list and push the change to the display, or call refresh() to push all rows to the displays. List.set(int, Object) performs better because it allows the data provider to push only those rows which have changed, and usually allows the display to re-render only a subset of the rows.

    So, you should first getList() and change it like this:

    myDataProvider.getList().clear();
    myDataProvider.getList().addAll(rowData);