TableCellRenderer

jorgeHX

Erfahrenes Mitglied
Also ich werde noch verrückt :-)

Alles was ich will, ist diesen doofen Renderer verstehen.

In meinem Programm nutze ich einen DefaultCellRenderer, also z.b.
myTable.setDefaultRenderer(Object.class, new ColoredTable());

In der Klasse ColoredTable will ich nun spezifisch festlegen, welche Zellen markiert sein sollen oder nicht.
Dazu lade ich aus meiner Datenbank alle Werte, die in der Tabelle mit einem grauen Kästchen hinterlegt sein sollen.

Mein Problem ist, dass dieser CellRenderer immer aufgerufen wird, sobald irgendwas an der Tabelle geschehen ist und dazu auch noch (row*column)mal.
Das ist ja super doof, da ich den Renderer ja eigentlich nur einmal zu Beginn brauche und dann wenn etwas neu eingefügt werden soll oder gelöscht werden soll.

Hat jemand vielleicht einen Tip, wie man einen individuellen CellRenderer anlegt und keinen DefaultCellRenderer? Ich finde einfach keine guten Links, die mir das erklären könnten.
 
Original geschrieben von jorgeHX

>Alles was ich will, ist diesen doofen Renderer verstehen.

Ist doch ganz einfach: Ein Renderer dient zum Zeichnen bzw. zur Visualisierung von Komponenten. ;)

>Mein Problem ist, dass dieser CellRenderer immer aufgerufen wird, sobald irgendwas an der Tabelle geschehen ist und dazu auch noch (row*column)mal.

>Das ist ja super doof, da ich den Renderer ja eigentlich nur einmal zu Beginn brauche und dann wenn etwas neu eingefügt werden soll oder gelöscht werden soll.

Dagegen kannst Du nichts machen, das erledigt Java/Swing automatisch. Fensterwechsel, Datenänderungen und was weiss ich was noch alles auslöst, dass der Renderer (erneut) gezeichnet wird.

>Hat jemand vielleicht einen Tip, wie man einen individuellen CellRenderer anlegt und keinen DefaultCellRenderer? Ich finde einfach keine guten Links, die mir das erklären könnten.

Siehe Thomas' Link, auch ich habe einen guten Link (schau mal in die Linksammlung) für alles, was mit Tabellen zu tun hat.
Einen eigenen Renderer zu schreiben ist doch ganz einfach. Du musst lediglich Deiner Rendererklasse das Interface TableCellRenderer "spendieren" und damit die Methode
Code:
Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)
implementieren. Der DefaultTableCellRenderer ist ja eigentlich ein JLabel. Möchtest Du etwas anderes haben, dann leite entsprechend Deinen Renderer von der gewünschten Komponente ab, z.B.

Code:
class MyRenderer extends JButton implements TableCellRenderer
{
 Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) 
 {
   setText("Hallo Welt");
   return this;
 }
}

und dann in Deiner Klasse
myTable.setDefaultRenderer(Object.class, new MyRenderer());
setzen, das ist alles.

Du kannst natürlich auch für andere Klassen eigene Renderer setzen, z.B.

myTable.setDefaultRenderer(Integer.class, new MyRenderer());

Du musst dann allerdings im TableModel eine Methode getColumnClass implementieren, in der für jede Spalte die zugehörige Klasse zugewiesen wird.
 
Re: Re: TableCellRenderer

Original geschrieben von Snape

Dagegen kannst Du nichts machen, das erledigt Java/Swing automatisch. Fensterwechsel, Datenänderungen und was weiss ich was noch alles auslöst, dass der Renderer (erneut) gezeichnet wird.


Mmh, aber genau das kann man nicht verhindern? Immerhin wird ja immer ein JComponent zurückgeliefert und das belastet doch den GarbageCollector oder nicht?
Bei mir würde das ja bedeuteten, dass bei jedem Fensterwechsel etc. die Daten aus der Datenbank immerwieder aufs Neue mit der Tabelle verglichen werden und bei Übereinstimmung erneut das farbliche Label gezeichnet wird. Ist das nicht ineffizient? Oder gibt es dafür keine andere Lösung?

Die Linksammlung ist sehr cool. Hatte ich noch gar nicht gesehen. Danke
 
Erstmal Danke für eure ununterbrochene Hilfe. Immerhin helft ihr mir schon seit geraumer Zeit....
Ich hoffe ihr seit nicht sauer wenn ich oft poste.

Die Links etc. waren hilfreich, allerdings stoße ich immerwieder auf Probleme, die wohl einfach zu lösen sind, wenn man das nötige Know-how hat.

1. Kann man in einer JTable die 7*7 groß ist, es so einstellen, dass bestimmte Zellen nicht selektierbar sind?

2. Kann man in einer JTable nur eine horizontale Linie haben? ich habe mit setShowGrid alles verschwinden lassen, aber eine Zeile sollte unterstrichen sein?

3. Kann man nur mit den Pfeiltasten der Tastatur von einer JTable in eine Andere springen, wenn man am Ende der Ersten angelangt ist?

Ich bin ich neu im Umgang mit JTables daher diese drei Fragen...
Sorry :(
 
Original geschrieben von jorgeHX

>1. Kann man in einer JTable die 7*7 groß ist, es so einstellen, dass bestimmte Zellen nicht selektierbar sind?

Nicht selektierbar? Hm, gute Frage, k.A. Reicht nicht editierbar auch?

>2. Kann man in einer JTable nur eine horizontale Linie haben? ich habe mit setShowGrid alles verschwinden lassen, aber eine Zeile sollte unterstrichen sein?

Sollte mit dem TableCellRenderer möglich sein, oder?

>3. Kann man nur mit den Pfeiltasten der Tastatur von einer JTable in eine Andere springen, wenn man am Ende der Ersten angelangt ist?

Ui, noch so eine Spezialfrage... k.A., aber ich denke das geht über KeyEvents.
Der Tabelle einen KeyListener zufügen und bei -> prüfen, ob die letzte Spalte (oder Zeile, je nachdem was Du möchtest) markiert ist, wenn ja: ab in die nächste Tabelle.

>Ich bin ich neu im Umgang mit JTables daher diese drei Fragen...

Auch wenn man schon ein alter Hase ist, sind das durchaus interessante Fragen. ;)

>Sorry :(

Brauchst Dich doch nicht zu entschuldigen für Fragen.
 
Re: Re: Re: TableCellRenderer

Original geschrieben von jorgeHX
>Mmh, aber genau das kann man nicht verhindern? Immerhin wird ja immer ein JComponent zurückgeliefert und das belastet doch den GarbageCollector oder nicht?

Wieso?

>Bei mir würde das ja bedeuteten, dass bei jedem Fensterwechsel etc. die Daten aus der Datenbank immerwieder aufs Neue mit der Tabelle verglichen werden

Dann hast Du m.E. einen Designfehler in Deinem Programm. Bei Fensterwechsel Daten aus der Datenbank neu laden hört sich ziemlich performancelastig an.

>und bei Übereinstimmung erneut das farbliche Label gezeichnet wird. Ist das nicht ineffizient?

Es wird so oft neu gezeichnet, und wohl aus gutem Grund. Ineffizienz sehe ich noch nicht, der Renderer wird ja nur einmal erzeugt und danach lediglich eine Referenz zurückgegeben.

>Oder gibt es dafür keine andere Lösung?

Ich würde einfach das Daten einlesen cleverer steuern. Nur dort, wo es wirklich nötig ist.

>Die Linksammlung ist sehr cool. Hatte ich noch gar nicht gesehen. Danke

Irre, was man mit/in Tabellen alles zaubern kann, gell? ;)
 
Da bin ich ja froh :)

Also nicht-editierbar reicht nicht. Ich möchte, dass bestimmte Zellen nur sichtbar aber nicht klickbar sind.... Weißt du das was?

Außerdem check ich nicht, wie man in einem JTable in die drunter-oder drüberliegende Reihe gelangt, wenn man nur die Pfeiltasten LINKS und RECHTS benutzt. Bei mir stoppt er immer am Ende der Reihe.... Hilfe :(

Den Rest versuch ich jetzt mal... Danke
 
Zuletzt bearbeitet:
Original geschrieben von jorgeHX

>Also nicht-editierbar reicht nicht. Ich möchte, dass bestimmte Zellen nur sichtbar aber nicht klickbar sind.... Weißt du das was?

Sorry, da muss ich passen. Würd mich auch mal interessieren, ob und wenn ja wie das geht.

>Außerdem check ich nicht, wie man in einem JTable in die drunter-oder drüberliegende Reihe gelangt, wenn man nur die Pfeiltasten LINKS und RECHTS benutzt. Bei mir stoppt er immer am Ende der Reihe.... Hilfe :(

Hehe, stimmt natürlich... :)
Wilst Du denn am Ende der ersten Zeile mit der -> in die erste Zelle der zweiten Zeile gelangen usw.? Oder was genau schwebt Dir vor?
Auf jeden Fall wirst Du vermutlich nicht drum herumkommen, Dich mit einem KeyListener auseinanderzusetzen.
 
Zurück