# JTable - TableModel



## redbomber (8. Mrz 2009)

Hi zusammen.
Ich besitze eine JTable die in eine JScrollPane eingebettet ist.
Für dieses JTable setze ich nun ein selbst definiertes TableModel (extends AbstractTableModel)

Nun möchte ich aber, wenn zum Beispiel das Fenster in dem sich die JScrollPane befindet vergrößert/verkleinert wird, dass die Tabelle mit neuer Zeilen/Spaltenanzahl neu gesetzt wird.

Bisher hatte ich das Problem wie folgt gelöst:
In der Klasse der JTable setze ich das TableModel immer neu!
Also ich erzeuge mir immer wieder ein neues TableModel, welches entsprechend die passende Zeilen/Spaltenanzahl besitzt.


Nun brauche ich aber eine Referenz auf das TableModel und kann daher nicht immer das TableModel neu erzeugen.
Mir erscheint das ohnehin etwas unpraktisch.
Wisst ihr wie ich das TableModel dazu bringe, sich neu "aufzubauen", also die Zeilen und Spaltenanzahl neu zu setzen?


----------



## Ebenius (8. Mrz 2009)

Da Du von AbstractTableModel erbst, musst Du nur die Daten im Tabellenmodell neu initialisieren und dann fireTableStructureChanged() rufen.

Ebenius


----------



## slawaweis (8. Mrz 2009)

redbomber hat gesagt.:


> Nun möchte ich aber, wenn zum Beispiel das Fenster in dem sich die JScrollPane befindet vergrößert/verkleinert wird, dass die Tabelle mit neuer Zeilen/Spaltenanzahl neu gesetzt wird.



ich vermute an dieser Stelle, dass Du im Grunde keine Tabelle, sondern eine horizontale JList mit Umbruch brauchst. Lese hier gleich das erste Beispiel:

How to Use Lists (The Java™ Tutorials > Creating a GUI with JFC/Swing > Using Swing Components)

Slawa


----------



## redbomber (8. Mrz 2009)

also du meinst dass ich in der JTable die Anzahl der Zeilen und Spalten neu setzen muss?
Bzw. wie soll ich die Daten im TableModel neu initialisieren?

Muss ich in der JTable folgendes aufrufen?


```
setModel(getModel());
```


----------



## redbomber (8. Mrz 2009)

Also bei mir gibt es folgendes Problem.
Das ganze ist ein Plugin von einem Framework. 
Die Daten die in der Tabelle dargestellt werden, an die komme ich erst in der JTable. Und zwar wenn addNotiy() aufgerufen wird.
Daher hatte ich das TableModel immer erst in der JTable dann danach gesetzt.

Nun möchte ich das TableModel einmalig bei der Initialisierung der JTable initialisieren.
Da stehen die Daten die dargestellt werden aber ja noch nicht zur Verfügung.

Jetzt habe ich versucht, überall wo ich früher das TableModel neu gesetzt habe, jetzt einfach

```
tableModel.fireTableStructureChanged();
```

aufzurufen.

Funktioniert aber nicht so ganz. 


@ slawaweis
Vielen Dank! Aber ich brauche schon eine JTable, da ich auf diese bereits meine implementierung abgestimmt habe.


----------



## Ebenius (9. Mrz 2009)

redbomber, ich meine das ungefähr so: [HIGHLIGHT="Java"]public class MyTableModel extends AbstractTableModel {

  private Object[][] data = {};

  @Override
  public int getRowCount() {
    return data.length;
  }

  @Override
  public int getColumnCount() {
    return data.length > 0 ? data[0].length : 0;
  }

  @Override
  public Object getValueAt(int rowIndex, int columnIndex) {
    return data[rowIndex][columnIndex];
  }

  @Override
  public void setValueAt(Object value, int rowIndex, int columnIndex) {
    data[rowIndex][columnIndex] = value;
    fireTableCellUpdated(rowIndex, columnIndex);
  }

  private static Object[][] twoDimArrayCopy(Object[][] array) {
    final int rowCount = array.length;
    final int columnCount = rowCount == 0 ? 0 : array[0].length;
    final Object[][] copy = new Object[rowCount][columnCount];
    for (int row = 0; row < rowCount; row++) {
      for (int col = 0; col < copy[row].length; col++) {
        copy[row][col] = array[row][col];
      }
    }

    return copy;
  }

  public Object[][] getData() {
    return twoDimArrayCopy(data);
  }

  public void setData(Object[][] data) {
    if (data == null) {
      throw new IllegalArgumentException( //
            "data not allowed null"); //$NON-NLS-1$
    }

    this.data = twoDimArrayCopy(data);
    fireTableStructureChanged();
  }
}[/HIGHLIGHT]

Ebenius


----------



## redbomber (10. Mrz 2009)

Ebenius, du bist ein Schatz 

Ich habe nun einfach eine Methode in meinem TableModel erstellt, welche das 
fireTableStructureChanged() 
event feuert.

Also immer wenn ich früher das neue TableModel gesetzt hatte, rufe ich einfach diese Methode für das Model auf
und die Tabelle wird neu gezeichnet.

(Die Daten setze ich bei mir nicht neu, da diese sich nicht ändern. Diese Daten werden in einer separaten Klasse gespeichert. Lediglich die Ansicht auf die Daten soll sich ändern.)


----------

