2014-11-14 6 views
5

haben Sie einen Blick auf den Code untenUngültige Sortierung auf Datum in JTable

import java.awt.*; 
import java.awt.event.*; 
import java.text.NumberFormat; 
import java.text.ParseException; 
import java.text.SimpleDateFormat; 
import java.util.*; 
import java.util.logging.Level; 
import java.util.logging.Logger; 
import javax.swing.*; 
import javax.swing.table.*; 

public class TableBasic extends JFrame 
{ 
    public TableBasic() 
    { 

     String[] columnNames = {"Date", "String", "Long", "Boolean"}; 
     Object[][] data = 
     { 
      {getJavaDate("13-11-2020"), "A", new Long(1), Boolean.TRUE }, 
      {getJavaDate("13-11-2018"), "B", new Long(2), Boolean.FALSE}, 
      {getJavaDate("12-11-2015"), "C", new Long(9), Boolean.TRUE }, 
      {getJavaDate("12-11-2015"), "D", new Long(4), Boolean.FALSE} 
     }; 

     final JTable table = new JTable(data, columnNames); 
     table.setPreferredScrollableViewportSize(table.getPreferredSize()); 
     table.setAutoCreateRowSorter(true); 
     table.getColumnModel().getColumn(0).setCellRenderer(tableCellRenderer); 

     // DefaultRowSorter has the sort() method 
     DefaultRowSorter sorter = ((DefaultRowSorter)table.getRowSorter()); 
     ArrayList list = new ArrayList(); 
     list.add(new RowSorter.SortKey(0, SortOrder.DESCENDING)); 
     sorter.setSortKeys(list); 
     sorter.sort(); 

     JScrollPane scrollPane = new JScrollPane(table); 
     getContentPane().add(scrollPane); 
    } 

    private TableCellRenderer tableCellRenderer = new DefaultTableCellRenderer() 
    { 

     SimpleDateFormat f = new SimpleDateFormat("dd-MM-yyyy"); 

     public Component getTableCellRendererComponent(JTable table,Object value, boolean isSelected, boolean hasFocus,int row, int column) 
     { 
      if(value instanceof Date) 
      { 
       value = f.format(value); 
      } 
      return super.getTableCellRendererComponent(table, value, isSelected,hasFocus, row, column); 
     } 
    }; 

    private Date getJavaDate(String s) 
    { 
     try { 
      SimpleDateFormat sdf = new SimpleDateFormat("dd-MM-yyyy"); 
      Date d = sdf.parse(s); 
      return d; 

     } catch (ParseException ex) { 
      Logger.getLogger(TableBasic.class.getName()).log(Level.SEVERE, null, ex); 
      return null; 
     } 
    } 



    public static void main(String[] args) 
    { 
     TableBasic frame = new TableBasic(); 
     frame.setDefaultCloseOperation(EXIT_ON_CLOSE); 
     frame.pack(); 
     frame.setLocationRelativeTo(null); 
     frame.setVisible(true); 
    } 
} 

Jetzt, nur versuchen, es zu sortieren das Date Feld. Es wird auf ungültige Weise sortiert! Unten ist das Ergebnis!

enter image description here

Warum wie dies geschieht dies? Ich habe sogar cell render verwendet!

Antwort

4

@ Sniper kein answert, aber ich kann nicht widerstehen, weil Ihr Code sehr kompliziert ist, falsch ausgelegt, verpassen es lighweight für ...

erforderlich

Das Schlüsselelement ist die Überschreibung von Tablemodel fehlt. getColumnClass() ist dies wichtig für Tisch

import java.awt.*; 
import java.text.DateFormat; 
import java.text.ParseException; 
import java.text.SimpleDateFormat; 
import java.util.*; 
import java.util.logging.Level; 
import java.util.logging.Logger; 
import javax.swing.*; 
import static javax.swing.JFrame.EXIT_ON_CLOSE; 
import javax.swing.table.*; 

public class TableBasic { 

    private JFrame frame = new JFrame(); 
    private String[] columnNames = {"Date", "String", "Long", "Boolean"}; 
    private Object[][] data = { 
     {getJavaDate("13-11-2020"), "A", new Double(1), Boolean.TRUE}, 
     {getJavaDate("13-11-2018"), "B", new Double(2), Boolean.FALSE}, 
     {getJavaDate("12-11-2015"), "C", new Double(9), Boolean.TRUE}, 
     {getJavaDate("12-11-2015"), "D", new Double(4), Boolean.FALSE} 
    }; 
    private DefaultTableModel model = new DefaultTableModel(data, columnNames) { 
     @Override 
     public Class<?> getColumnClass(int column) { 
      return getValueAt(0, column).getClass(); 
     } 
    }; 
    private JTable table = new JTable(model); 
    private JScrollPane scrollPane = new JScrollPane(table); 
    private static final DateFormat DATE_FORMAT = new SimpleDateFormat("dd/MM/yyyy"); 

    public TableBasic() { 
     table.setPreferredScrollableViewportSize(table.getPreferredSize()); 
     table.setAutoCreateRowSorter(true); 
     setRenderers(); 
     // DefaultRowSorter has the sort() method 
     table.getRowSorter().toggleSortOrder(0); 
     frame.add(scrollPane); 
     frame.setDefaultCloseOperation(EXIT_ON_CLOSE); 
     frame.pack(); 
     frame.setLocationRelativeTo(null); 
     frame.setVisible(true); 
    } 

    private void setRenderers() { 
     //TableColumnModel m = table.getColumnModel(); 
     //"Integer", "String", "Interger", "Double", "Boolean", "Double", "String", "Boolean", "Date" 
     table.setDefaultRenderer(Date.class, new DateRenderer()); 
    } 

    private Date getJavaDate(String s) { 
     try { 
      SimpleDateFormat sdf = new SimpleDateFormat("dd-MM-yyyy"); 
      Date d = sdf.parse(s); 
      return d; 

     } catch (ParseException ex) { 
      Logger.getLogger(TableBasic.class.getName()).log(Level.SEVERE, null, ex); 
      return null; 
     } 
    } 

    public static void main(String[] args) { 

     EventQueue.invokeLater(new Runnable() { 
      @Override 
      public void run() { 
       TableBasic frame = new TableBasic(); 
      } 
     }); 
    } 

    private class DateRenderer extends DefaultTableCellRenderer { 

     private static final long serialVersionUID = 1L; 

     @Override 
     public Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) { 
      super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column); 
      if (!(value instanceof Date)) { 
       return this; 
      } 
      setText(DATE_FORMAT.format((Date) value)); 
      return this; 
     } 
    } 
} 
+0

Danke. Ich schätze die Antwort. –

+0

@Sniper Sie sind herzlich willkommen – mKorbel

5

Die Tabelle nicht weiß, dass die Spalte immer Date-Instanzen enthält und dass es muss also chronologisch sortieren, wenn Sie es, dass die Informationen geben, durch Überschreiben der getColumnClass() Methode des Tabellenmodell:

final Class<?>[] columnClasses = new Class<?>[] {Date.class, String.class, Long.class, Boolean.class}; 

DefaultTableModel model = new DefaultTableModel(...) { 
    @Override 
    public Class<?> getColumnClass(int column) { 
     return columnClasses[column]; 
    } 
}); 
JTable table = new JTable(model); 

Zusatz Bonus: Die numerischen und booleschen Spalten werden dann automatisch korrekt gerendert und sortiert.

+0

Danke für die Antwort. An welcher Stelle sollte ich deinen Code platzieren? –

+0

und, ich bin nicht klar über den Code, Mind bitte ein vollständiges praktikables Beispiel bitte? –

+0

@munyul: Ich habe es schon getan, und das Modell ohne Parameter eingestellt. Aber es gibt einfach 'ArrayIndexOutOfBounds Exception' –

2

Hier ist die Antwort funktioniert das Sortieren, den Code von JB Nizet mit

String[] columnNames = {"Date", "String", "Long", "Boolean"}; 
    Object[][] data = 
    { 
     {getJavaDate("13-11-2020"), "A", new Long(1), Boolean.TRUE }, 
     {getJavaDate("13-11-2018"), "B", new Long(2), Boolean.FALSE}, 
     {getJavaDate("12-11-2015"), "C", new Long(9), Boolean.TRUE }, 
     {getJavaDate("12-11-2015"), "D", new Long(4), Boolean.FALSE} 
    }; 

    final Class<?>[] columnClasses = new Class<?>[] {Date.class, String.class, Long.class, Boolean.class}; 

    DefaultTableModel model = new DefaultTableModel() { 
     @Override 
     public Class<?> getColumnClass(int column) { 
      return columnClasses[column]; 
     } 
    }; 
    model.setDataVector(data, columnNames); 

    final JTable table = new JTable(model); 

Dieser Code wird in Ihren Konstruktor übernommen und ersetzt die ersten Zeilen darin.