'Sorting Jtable by sort order(multi level sort)

I have a JTable and a TableRowSorter which I'd like to sort columns by sorting order for example if i have this table

(3,3,1)
(4,3,2)
(2,4,3)
(1,2,4)
(5,2,1)
(3,1,1)
(2,2,5)
(4,5,4)
(1,1,3)
(1,3,2)

and when i click on A header it will be sort like

(1,2,4)
(1,1,3)
(1,3,2)
(2,4,3)
(2,2,5)
(3,3,1)
(3,1,1)
(4,5,4)
(4,5,4)
(5,2,1)

but what i want is when i click on the B header for sorting this column,A column should be still sorted like this

(1,1,3)
(1,2,4)
(1,3,2)
(2,2,5)
(2,4,3)
(3,1,1)
(3,3,1)
(4,3,2)
(4,5,4)
(5,2,1)

and when i click column c it will be the same



Solution 1:[1]

This is not hard to implement but it will require to use JXTable from SwingX to start with. JXTable extends JTable to provide some core grid functionalities out of the box. However, JXTable still maintains the same sort order which is not the expected multi column sorting (at least not for me). Take look at the following points:

First have a good understanding of the sortKeys concept, which is the list that holds the who is sorted and in which column index order.

  1. Extend org.jdesktop.swingx.sort.TableSortController and override toggleSortOrder method. This method organizes the sort order across the columns (sortKeys). Make sure that the sortKeys list is always in the first clicked column remains first order.

  2. Another thing you will realize that removing a column doesn't remove its sorted state which means that when you add the column back, it will remain sorted (with sort icon in the header). It might be a personal thing, a UX expert would know better but I think it is not an expected behavior. To solve this, extend javax.swing.event.TableColumnModelListener and remove the sortKey of the column at columnRemoved event. To bind the listener: table.getColumnModel().addColumnModelListener(YourTableColumnModelListener(table));

  3. Also, make sure that maxSortKeys is also maintained because JXTable will only sort 3 columns by default. Either set this value to your initial column count or update it each time a column is added/removed (point 2).

  4. Finally, if you need to show the sort order in the header, take a look at javax.swing.table.DefaultTableCellRenderer. You will need to extend it and override the getTableCellRendererComponent method for look&feel stuff.

PS. SwingX is at version 1.6.x at the time of writing, and there is not a good online documentation (not even hosted javadocs) so you will need to use the javadocs from the source code to find your way.

One last note; probably you can implement these without adding SwingX layer. It might just require more digging.

Solution 2:[2]

You made me look at really old code, but it still works:

Table Header Demo

The demo app is here, you'll need to checkout the Git HVLayout-master to get it running. But you can also just browse for the relevant source code. To get it running (tested with Java 11):

git clone https://github.com/fwi/HVLayout.git
cd HVLayout
mvn verify
cd swing-demo/target/
# For Windows use 'javaw' instead of 'java'
java -cp swing-demo-lib.jar nl.fw.swing.demo.TableSortDemo

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2