2013-11-14 3 views
3

У меня есть JTable, который можно сортировать, вызывая сортировку по вызову setAutoCreateRowSorter (true) при инициализации). Я сортирую эту таблицу программно, и я хотел бы отключить обработку событий по умолчанию в заголовке таблицы, так что таблица может быть отсортирована программно только. Как его достичь?JTable сортировка программно только

рабочая часть кода будет:

public class SortTable extends JDialog { 

    private JTable table; 

    DefaultRowSorter<TableModel, String> sorter; 

    public SortTable() { 
     JScrollPane scrollPane = new JScrollPane(); 
     setBounds(0, 0, 300, 200); 
     getContentPane().setLayout(new BorderLayout()); 
     getContentPane().add(scrollPane, BorderLayout.CENTER); 

     //-------most important stuff------------------- 
     table = new JTable(); 
     table.setAutoCreateRowSorter(true); //enabling sorting 
     table.setModel(createModel()); 
     sorter = (DefaultRowSorter<TableModel, String>)table.getRowSorter(); //store sorter to sort programatically later on 
     //----------------------------------------------- 

     scrollPane.setViewportView(table); 
     JPanel buttonPane = new JPanel(); 
     buttonPane.setLayout(new FlowLayout(FlowLayout.RIGHT)); 
     getContentPane().add(buttonPane, BorderLayout.SOUTH); 
     buttonPane.add(new JButton(getSortAction())); 
    } 

    private AbstractAction getSortAction() { 
     return new AbstractAction("Sort") { 

      @Override 
      public void actionPerformed(ActionEvent e) { 
       sorter.setSortKeys(Arrays.asList(new SortKey(0,SortOrder.ASCENDING))); 
       sorter.sort(); //sorting programatically 

      } 
     }; 
    } 

    private DefaultTableModel createModel() { 
     return new DefaultTableModel(
      new Object[][] { 
       {"1", "3"}, 
       {"5", "2"}, 
       {"4", null}, 
      }, 
      new String[] { 
       "A", "B" 
      } 
     ); 
    } 
} 

Этот пример является JDialog содержащий JTable с Sort кнопку. Нажатие этой кнопки приведет к сортировке столбца A по возрастанию. Однако кнопка не является единственным способом сортировки таблицы - мы можем просто щелкнуть заголовок таблицы, чтобы изменить сортировку. Мой вопрос заключается в том, как сделать кнопку единственным способом сортировки таблицы. Было бы также полезно знать, как избавиться от стрелки, которая появляется при изменении сортировки.

+2

similair вопросы были заданы в этом и в прошлом месяце несколько раз, поиск BZ нажмите на RowSorter тег, или TableRowSorter – mKorbel

+1

@mKorbel darn, я должен иногда читать api doc ;-) – kleopatra

ответ

4

Чтение сообщений по аналогичным вопросам (например, @mKorbel) и экспериментирование. Мне удалось найти решение. Ответ на главный вопрос: Используйте метод setSortable(int index, boolean sortable) метода DefaultRowSorter. Кажется очевидным, но интересным является то, что этот метод отключает сортировку столбца при использовании toggleSortOrder(int index) RowSorter, но он игнорируется при использовании метода DefaultRowSorter sort(). Это какая-то непоследовательность? Так или иначе, это оставляет дверь открытой для трюка. Теперь я могу сделать:

 for (int i=0 ; i<table.getColumnCount() ; i++) { 
      sorter.setSortable(i, false); 
     } 

... и вуаля - таблица не может быть отсортирован заголовки таблицы больше, но это может быть отсортирован программно. Если кто-то сталкивается с странным требованием скрывать эти значки индикатора порядка сортировки, как у меня, есть пути. Сначала будет глобальный эффект, и мне это не нравится - задайте соответствующие свойства UIManager.

 UIManager.put("Table.ascendingSortIcon", new EmptyIcon()); 
     UIManager.put("Table.descendingSortIcon", new EmptyIcon()); 

Лучше один, чтобы украсить по умолчанию визуализатор в TableHeader:

 final TableCellRenderer defaultRenderer = table.getTableHeader().getDefaultRenderer(); 
     table.getTableHeader().setDefaultRenderer(new TableCellRenderer() { 

      @Override 
      public Component getTableCellRendererComponent(JTable table, 
        Object value, boolean isSelected, boolean hasFocus, 
        int row, int column) { 
       JLabel label = (JLabel)defaultRenderer.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column); 
       label.setIcon(null); 
       return label; 
      } 

     }); 
+1

_Is, что своего рода несогласованность_ нет, он разработан (и задокументирован), чтобы точно решить ваше требование :-) – kleopatra

+0

Да, это так, вы правы, я пропустил это. С другой стороны, класс JTableHeader имеет этот метод setReorderingAllowed, который может отключить переупорядочение столбцов. Честно говоря, я считаю, что было бы более интуитивным иметь setRowSortingAllowed или smth. Это более естественно означает, что заголовок прослушивает события мыши или нет. Фактический механизм сортировки (RowSorter) не будет задействован вообще. – macias

+0

полностью согласен, хороший аргумент :-) На самом деле, я забыл точный смысл сортируемого имущества и предложил взломать (удалил). Вероятно, даже допустил ошибку в SwingX 'sortController, у которого есть дополнительная api для программной сортировки (setSortOrder), которая ничего не делает, если столбец не сортируется. – kleopatra

Смежные вопросы