Ich will eine Tabelle (nur eine Spalte) sortieren. Dies soll mit einem Klick auf einen Button im Header erfolgen (vorest ein JButton, später dann eine adaptierte Klasse mit Pfeil (v, ^ bzw. -).
Es gelint mir, mit einem eigenen Rendere wohl einen Button in der Kopfzeile zu platzieren, aber der Button reagiert nicht. Ich habe dazu nichts in der API gefunden (JTableHeader, ColumnModel usw.). Und die Beispiel im Internet sind mir zu mühsam. Will soweit möglich mit Swing auskommen und nur kleine Ergänzungen machen.
Frage: Warum reagiert der JButton im Heder der Tablle (JTableHeader) nicht auf den Klick?
Hier ein Beispiel-Code:
import javax.swing.*;
import javax.swing.table.*;
import javax.swing.event.*;
import java.awt.*;
import java.awt.event.*;
public class TableDemo extends JFrame
{
private JTable theTable;
private TableModel model;
public TableDemo(TableModel _model){
super ("Karteikasten");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
model = _model;
//
init();
//
pack();
setVisible(true);
}
private void init(){
theTable = new JTable(model);
theTable.getColumnModel().getColumn(0).setHeaderRenderer(new CardTableHeaderRenderer(model));
theTable.getSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
theTable.getSelectionModel().addListSelectionListener(new ListSelectionListener(){
public void valueChanged(ListSelectionEvent event){
onSelection(event);
}
});
JScrollPane tablePane = new JScrollPane(theTable, ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS, ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);
getContentPane().add(tablePane, BorderLayout.WEST);
}
private void onSelection(ListSelectionEvent event){
System.out.println("Demo: Tabelle selektiert");
}
public static void main(String[] args)
{
Model m = new Model();
TableDemo gui = new TableDemo(m);
}
}
/***********************************/
class Model extends AbstractTableModel
{
final int[] values = {13, 45, 3, 56, 22, 23, 67, 88, 23, 8, 1, 56, 34, 78, 29, 55, 78};
public String getColumnName(int col){return "Zahlenreihe";}
public int getColumnCount() { return 1;}
public int getRowCount() { return 17;}
public Object getValueAt(int row, int col) { return new Integer(values[row]); }
public void sortByNr(){
System.out.println(" nun wird sortiert");
// Werte stehen dann in einer Klasse, die Interface Comparable implementiert
// zur Nutzung mit einer Collection Collections.sort()
}
};
class CardTableHeaderRenderer extends DefaultTableCellRenderer
{
// Farben für den Hintergerud
final private Color BG = new Color(255,255,0);
private JPanel headerPanel;
private JButton sortBtn;
private TableModel model;
CardTableHeaderRenderer(TableModel m){
super();
model = m;
//
sortBtn = new JButton("*");
sortBtn.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent event){
/* Warum geht das nicht?
Wer verhindert, dass der Button geklickt
werden kann
*/
onSort();
}
});
//
headerPanel = new JPanel(new BorderLayout());
headerPanel.setBackground(BG);
headerPanel.add(sortBtn, BorderLayout.EAST);
headerPanel.add(new JSeparator(), BorderLayout.SOUTH);
}
/*
Diese Methode wird durch JTable aufgerufen.
Die Titelzeile erhält eine Schaltfläche für das Sortieren.
*/
public Component getTableCellRendererComponent(JTable table, Object value,
boolean isSelected, boolean hasFocus,
int row,int column){
headerPanel.add(new JLabel((String)value), BorderLayout.WEST);
return headerPanel;
}
private void onSort(){
((Model) model).sortByNr();
}
}
Es gelint mir, mit einem eigenen Rendere wohl einen Button in der Kopfzeile zu platzieren, aber der Button reagiert nicht. Ich habe dazu nichts in der API gefunden (JTableHeader, ColumnModel usw.). Und die Beispiel im Internet sind mir zu mühsam. Will soweit möglich mit Swing auskommen und nur kleine Ergänzungen machen.
Frage: Warum reagiert der JButton im Heder der Tablle (JTableHeader) nicht auf den Klick?
Hier ein Beispiel-Code:
import javax.swing.*;
import javax.swing.table.*;
import javax.swing.event.*;
import java.awt.*;
import java.awt.event.*;
public class TableDemo extends JFrame
{
private JTable theTable;
private TableModel model;
public TableDemo(TableModel _model){
super ("Karteikasten");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
model = _model;
//
init();
//
pack();
setVisible(true);
}
private void init(){
theTable = new JTable(model);
theTable.getColumnModel().getColumn(0).setHeaderRenderer(new CardTableHeaderRenderer(model));
theTable.getSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
theTable.getSelectionModel().addListSelectionListener(new ListSelectionListener(){
public void valueChanged(ListSelectionEvent event){
onSelection(event);
}
});
JScrollPane tablePane = new JScrollPane(theTable, ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS, ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED);
getContentPane().add(tablePane, BorderLayout.WEST);
}
private void onSelection(ListSelectionEvent event){
System.out.println("Demo: Tabelle selektiert");
}
public static void main(String[] args)
{
Model m = new Model();
TableDemo gui = new TableDemo(m);
}
}
/***********************************/
class Model extends AbstractTableModel
{
final int[] values = {13, 45, 3, 56, 22, 23, 67, 88, 23, 8, 1, 56, 34, 78, 29, 55, 78};
public String getColumnName(int col){return "Zahlenreihe";}
public int getColumnCount() { return 1;}
public int getRowCount() { return 17;}
public Object getValueAt(int row, int col) { return new Integer(values[row]); }
public void sortByNr(){
System.out.println(" nun wird sortiert");
// Werte stehen dann in einer Klasse, die Interface Comparable implementiert
// zur Nutzung mit einer Collection Collections.sort()
}
};
class CardTableHeaderRenderer extends DefaultTableCellRenderer
{
// Farben für den Hintergerud
final private Color BG = new Color(255,255,0);
private JPanel headerPanel;
private JButton sortBtn;
private TableModel model;
CardTableHeaderRenderer(TableModel m){
super();
model = m;
//
sortBtn = new JButton("*");
sortBtn.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent event){
/* Warum geht das nicht?
Wer verhindert, dass der Button geklickt
werden kann
*/
onSort();
}
});
//
headerPanel = new JPanel(new BorderLayout());
headerPanel.setBackground(BG);
headerPanel.add(sortBtn, BorderLayout.EAST);
headerPanel.add(new JSeparator(), BorderLayout.SOUTH);
}
/*
Diese Methode wird durch JTable aufgerufen.
Die Titelzeile erhält eine Schaltfläche für das Sortieren.
*/
public Component getTableCellRendererComponent(JTable table, Object value,
boolean isSelected, boolean hasFocus,
int row,int column){
headerPanel.add(new JLabel((String)value), BorderLayout.WEST);
return headerPanel;
}
private void onSort(){
((Model) model).sortByNr();
}
}