JTable的非实时/非实时排序

时间:2012-05-31 22:46:30

标签: java swing jtable live tablerowsorter

当表处于排序模式(使用RowSorter)时,似乎表的大部分时间是实时排序的。例如,每当我添加新行时,表都会自动排序(编辑单元格除外)。我想知道是否有任何方法可以禁用此实时排序行为。

我想要做的是:在对表进行排序后,升序或降序,然后分拣机保持当前的排序状态并停止实时排序。然后可以在底部添加新行,并且可以上下移动选定的行,并且表更新视图模型中的所有更改。

@trashgod:谢谢你的回答。我实际上喜欢本地roworter方法,因为我可以在三态(升序,降序和未排序)中循环列状态。如果使用Collections.sort,我将不得不创建一个变量来保存原始行顺序,然后每次排序。

2 个答案:

答案 0 :(得分:2)

您可以使用Collections.sort()和自定义TableModel(例如显示为here的自定义RowSorter)来排序Comparator独立于enum Sort { ASCENDING, DESCENDING; } class RecordComparator implements Comparator<Record> { public RecordComparator(Sort sort, ...) { ... } } 的行接受指定排序方向的参数。

{{1}}

答案 1 :(得分:0)

看起来你想要的是能够对表进行排序,但是能够在不更改表排序顺序的情况下添加更多行。即使有可能,您也必须重写DefaultRowSorterTableRowSorter(两者都可用的来源)。原因是当前实现旨在保持一致的排序顺序(不考虑何时添加行)。你可能无法扩展TableRowSorter来克服这个问题,因为它的父类有很多私有函数与我刚刚描述的设计相关联。

我上面描述的是干净的方式。这是另一种方法,每次要插入新行时都要这样做:

  1. 在地图中保存视图的当前排序顺序。我使用了一个hashmap(postion)将sort列的第i行中的每个对象映射到它在视图中的位置。 position.put(tableModel.getValueAt(i, column), sorter.convertRowIndexToView(i));

  2. 创建一个比较器,使用上面创建的地图对传入数据进行排序。将TableRowSorter的列比较器设置为新创建的比较器。然后调用sorter.sort(),这是必要的,因为DefaultRowSorter需要缓存比较器。比较器将现有对象放在当前位置,并在最后放置新对象(在插入过程中创建)。

  3. 在表模型中执行行插入。在我的代码中,我将3个随机的Integer,Boolean和Double值添加到表格中的3列。

  4. 通过将值设置为null sorter.setComparator(sortKeys.get(0).getColumn(), null);来删除#3中添加的比较器。这样,下次在列上切换排序时,它将使用默认比较器而不是虚拟比较器。 / p>

  5. 完整代码如下。每次按下按钮时,它都会向表中添加一行。请注意我没有使用sortkeys&gt;进行测试。 1或过滤器(我会留给你)。让我知道你对这个黑客的看法。

    private void insertRowButtonActionPerformed(java.awt.event.ActionEvent evt) {
        TableRowSorter<TableModel> sorter = (TableRowSorter<TableModel>)jTable1.getRowSorter();
        final HashMap<Object, Integer> position = new HashMap<Object, Integer>();
        List<? extends SortKey> sortKeys = sorter.getSortKeys();
    
        if(!sortKeys.isEmpty()){
            SortKey sortKey = sortKeys.get(0);
            int column = sortKey.getColumn();
            TableModel tableModel = sorter.getModel();
            int n = sorter.getModelRowCount();
            final SortOrder sortOrder = sortKey.getSortOrder();
            for(int i=0;i<n;i++){
                position.put(tableModel.getValueAt(i, column), sorter.convertRowIndexToView(i));
            }
            //add dummy comparator
            sorter.setComparator(column, new Comparator<Object>(){
                public int compare(Object o1, Object o2) {
                    int obj1Position = position.containsKey(o1) ? position.get(o1):position.size();
                    int obj2Position = position.containsKey(o2) ? position.get(o2):position.size();
                    return sortOrder == SortOrder.DESCENDING ? obj2Position - obj1Position:obj1Position - obj2Position;
                }
            });
            sorter.sort();
        }
    
        /////////////insert row///////////////////
        DefaultTableModel tableModel = (DefaultTableModel)jTable1.getModel();
        tableModel.addRow(new Object[]{rand.nextInt(), rand.nextBoolean(), rand.nextDouble()});
        /////////////end insert row///////////////
    
        //remove dummy comparator
        if(!sortKeys.isEmpty()){
            sorter.setComparator(sortKeys.get(0).getColumn(), null);
        }
    }