JTable Rendering Problem

pabatribick

Grünschnabel
Hey Community!

Habe ein Renderer Problem mit meiner JTable.
Meine 2. Spalte namens message wird nicht gerendert und vom Array einfach in die Tabelle eingetragen.

Hier mein Code:

Code:
import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import javax.swing.table.*;

public class JButtonTableExample extends JFrame {

  public JButtonTableExample(){
    super( "JButtonTable Example" );
    
    DefaultTableModel dm = new DefaultTableModel() {
        public boolean isCellEditable(int row, int column) {
            if (column == 1) {
                return false;
            } else {
                return true;
            }
          }
    };
    dm.setDataVector(new String[][]{{"Username","Texttext"},
            {"Username","Texttext 2 Text Text Text Text Text Text Text Text Text Text Text"},
            {"Username", "Text!"}},
            new String[]{"username","message"});
                     
    JTable table = new JTable(dm);
    table.setShowGrid(false);
    table.setCellSelectionEnabled(false);
    table.setFocusable(false);
    table.setTableHeader(null);
    table.getColumn("username").setCellRenderer(new ButtonRenderer());
    table.getColumn("username").setCellEditor(new ButtonEditor(new JCheckBox()));
    table.getColumn("message").setCellRenderer(new LabelRenderer());
    table.getColumn("message").setCellEditor(new LabelEditor(new JCheckBox()));
    table.getColumn("username").setMinWidth(200);
    table.getColumn("username").setMaxWidth(200);
    JScrollPane scroll = new JScrollPane(table);
    getContentPane().add( scroll );
    setSize( 400, 100 );
    setVisible(true);
  }

  public static void main(String[] args) {
    JButtonTableExample frame = new JButtonTableExample();
    frame.addWindowListener(new WindowAdapter() {
      public void windowClosing(WindowEvent e) {
        System.exit(0);
      }
    });
  }
}

Die Renderer:

ButtonEditor.java
Code:
import java.awt.Component;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

import javax.swing.DefaultCellEditor;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JOptionPane;
import javax.swing.JTable;
import javax.swing.SwingConstants;

public class ButtonEditor extends DefaultCellEditor {
  protected JButton button;
  private String    label;
  private boolean   isPushed;

  public ButtonEditor(JCheckBox checkBox) {
    super(checkBox);
    button = new JButton();
    button.setOpaque(true);
    button.setHorizontalAlignment(SwingConstants.LEFT);
    button.addActionListener(new ActionListener() {
      public void actionPerformed(ActionEvent e) {
        fireEditingStopped();
      }
    });
  }

  public Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column) {
    if (isSelected) {
      button.setForeground(table.getSelectionForeground());
      button.setBackground(table.getSelectionBackground());
    } else {
      button.setForeground(table.getForeground());
      button.setBackground(table.getBackground());
    }
    label = (value ==null) ? "" : value.toString();
    button.setText( label );
    isPushed = true;
    return button;
  }

  public Object getCellEditorValue() {
    if (isPushed)  {
      // 
      // 
      JOptionPane.showMessageDialog(button ,label + ": Ouch!");
      // System.out.println(label + ": Ouch!");
    }
    isPushed = false;
    return new String( label ) ;
  }
  
  public boolean stopCellEditing() {
    isPushed = false;
    return super.stopCellEditing();
  }

  protected void fireEditingStopped() {
    super.fireEditingStopped();
  }
}

ButtonRenderer.java
Code:
import java.awt.*;
import javax.swing.*;
import javax.swing.table.*;

public class ButtonRenderer extends JButton implements TableCellRenderer {

  public ButtonRenderer() {
    setOpaque(true);
    this.setHorizontalAlignment(SwingConstants.LEFT);
  }
  
  public Component getTableCellRendererComponent(JTable table, Object value,
                   boolean isSelected, boolean hasFocus, int row, int column) {
    if (isSelected) {
      setForeground(table.getSelectionForeground());
      setBackground(table.getSelectionBackground());
    } else{
      setForeground(table.getForeground());
      setBackground(UIManager.getColor("Button.background"));
    }
    setText( (value ==null) ? "" : value.toString() );
    return this;
  }
}

LabelEditor.java
Code:
import java.awt.Component;

import javax.swing.DefaultCellEditor;
import javax.swing.JCheckBox;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JTable;

public class LabelEditor extends DefaultCellEditor {
    
    private JLabel label;
    private String obj_label;
    
    public LabelEditor(JCheckBox checkBox) {
        super(checkBox);
        label = new JLabel();
    }
    
    public Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column) {
        obj_label = value.toString();
        label.setText(obj_label);
        return label;
      }
    
    public Object getCellEditorValue() {
        return new String( this.obj_label ) ;
      }

}

LabelRenderer.java
Code:
import java.awt.Component;
import java.awt.Dimension;

import javax.swing.JTable;
import javax.swing.JTextArea;
import javax.swing.table.TableCellRenderer;

public class LabelRenderer extends JTextArea implements TableCellRenderer {
    
    public void LabelRenderer() {
        this.setOpaque(true);
        this.setEditable(false);
        this.setLineWrap(true);
        this.setWrapStyleWord(true);
    }
 
    @Override
    public Component getTableCellRendererComponent(JTable table, Object value,
            boolean isSelected, boolean hasFocus, int row, int column) {
        setText(value.toString());
        return this;
    }
}

Das seltsame ist dabei, dass die 1. Spalte komplett korrekt gerendert wird.

Habe ich etwas bei dem Label vergessen für die 2. Spalte? Ich möchte den Label gerne mehrzeilig haben, damit der Text nicht aus dem Fenster springt bzw. ins nichts verlauft.
 
Hi,
bei sovielen Dateien bietet es sich fast schon an eine kleine Zip-Datei zu machen und die hochzuladen ;) ist einfach viel angenehmer eine Datei zu laden als x über Copy&Paste zu erzeugen.

Dein Problem ist im LabelRenderer. Dein Constructor hat ein void da stehen.

Java:
import java.awt.Component;
import java.awt.Dimension;
 
import javax.swing.JTable;
import javax.swing.JTextArea;
import javax.swing.table.TableCellRenderer;
 
public class LabelRenderer extends JTextArea implements TableCellRenderer {
    
    public LabelRenderer() { // vorher stand hier public void ...
        this.setOpaque(true);
        this.setEditable(false);
        this.setLineWrap(true);
        this.setWrapStyleWord(true);
    }
 
    @Override
    public Component getTableCellRendererComponent(JTable table, Object value,
            boolean isSelected, boolean hasFocus, int row, int column) {
        setText(value.toString());
        return this;
    }
}

Danach funktioniert dein Zeilenumbruch. Du wirst aber nichts sehen weil sich die Spalte nicht vergrößert. Das musst du dann noch dazu Basteln.

Gruß,
swas
 
Zurück