2017-03-16 3 views
1

Ich habe eine vernünftige einfache JTable, die ich jede Sekunde aktualisieren möchte.Wie `fireTableDataChanged` richtig ausgelöst wird

Um dies zu tun, habe ich festgestellt, dass Sie verwenden sollen, aber nach mehreren Versuchen kann ich es immer noch nicht zum Laufen bringen.

import java.awt.event.ActionEvent; 
import java.awt.event.ActionListener; 

import javax.swing.JFrame; 
import javax.swing.JPanel; 
import javax.swing.JScrollPane; 
import javax.swing.JTable; 
import javax.swing.Timer; 
import javax.swing.table.DefaultTableModel; 

@SuppressWarnings("serial") 
public class Changer extends JFrame { 
    int phils = 1; 
    int daves = 2; 
    int bobs = 3; 
    String[] cols = {"Name", "Num"}; 
    Object[][] data = {{"Phil", phils}, 
         {"Dave", daves}, 
         {"Bob", bobs}}; 
    DefaultTableModel dm = new DefaultTableModel(data, cols); 
    JTable table = new JTable(dm); 

    public Changer() { 
     super("Changer"); 

     JPanel p = new JPanel(); 
     p.add(new JScrollPane(table)); 
     add(p); 
     pack(); 
     setVisible(true); 
     setDefaultCloseOperation(EXIT_ON_CLOSE); 

     Timer t = new Timer(1000, new ActionListener(){ 
      @Override 
      public void actionPerformed(ActionEvent e) { 
       phils++; 
       daves++; 
       bobs++; 
       data = new Object[][] {{"Phil", phils}, 
          {"Dave", daves}, 
          {"Bob", bobs}}; 
       dm.fireTableDataChanged(); 
       repaint(); 
       revalidate(); 
       table.repaint(); 
       table.revalidate(); 

       System.out.println(phils + ", " + daves + ", " + bobs); 
      } 
     }); 

     t.start(); 
    } 

    public static void main(String[] args) { 
     new Changer(); 
    } 
} 

Zunächst ich

Timer t = new Timer(1000, new ActionListener(){ 
    @Override 
    public void actionPerformed(ActionEvent e) { 
     phils++; 
     daves++; 
     bobs++; 

     dm.fireTableDataChanged(); 
    } 
}); 

hatte gerade Da die docs es funktionieren würde vorschlagen scheinen, wenn die Werte aktualisiert werden.

Dann habe ich versucht

Timer t = new Timer(1000, new ActionListener(){ 
    @Override 
    public void actionPerformed(ActionEvent e) { 
     phils++; 
     daves++; 
     bobs++; 

     data = new Object[][] {{"Phil", phils}, 
       {"Dave", daves}, 
       {"Bob", bobs}}; 
     dm.fireTableDataChanged(); 
    } 
}); 

Um zu sehen, ob ich physisch die Variable data aktualisieren musste.

Schließlich habe ich alle validates und Bemalungen zu sehen, ob das einen Unterschied machen würde, und ein System.out.println nur für den Fall hatte ich einen Fehler mit dem Timer irgendwie gemacht. Was mache ich falsch?

Antwort

2

Die DefaultTableModel Sie verwenden erstellt eine Vector von Ihrem Object Array und verwendet diese als Daten:

protected static Vector convertToVector(Object[][] anArray) { 
     if (anArray == null) { 
      return null; 
     } 
     Vector<Vector> v = new Vector<Vector>(anArray.length); 
     for (Object[] o : anArray) { 
      v.addElement(convertToVector(o)); 
     } 
     return v; 
    } 

Dies bedeutet, dass das Array zu ersetzen (oder sogar seinen Inhalt zu ändern) nicht magisch reflektieren jede Änderung am Modell.

Was Sie können, bevor tun dm.fireTableDataChanged() Aufruf entweder

die Daten des Modells ersetzen

dm.setDataVector(data, cols); 

Oder alle Zeilen löschen und legen Sie die neuen

while(dm.getRowCount()>0){ 
     dm.removeRow(0); 
} 
dm.addRow(new Object[] {"Phil", phils }); 
dm.addRow(new Object[] {"Dave", daves }); 
dm.addRow(new Object[] {"Bob", bobs }); 

Oder suchen Sie die Zeile passend t Name, den er, aktualisieren Sie die Zeile:

updateRow(new Object[] {"Phil", phils }); 
updateRow(new Object[] {"Dave", daves }); 
updateRow(new Object[] {"Bob", bobs }); 

mit diesem updateRow Verfahren weitgehend von Java JTable update row inspiriert:

private void updateRow(Object[] data) { 

     String userName = data[0].toString(); 
     for (int i = 0; i < dm.getRowCount(); i++) 
      if (dm.getValueAt(i, 0).equals(userName)) 
       for (int j = 1; j < data.length; j++) 
        dm.setValueAt(data[j], i, j); 
    } 
+1

'dm.setDataVector (Daten, cols);' tat es dank – Dan

Verwandte Themen