6

クリックすると機能するJButtonを備えたセルにJPanelを配置できるようにしたい。

セルエディタに関するハウツーを探しましたが、すべての例で、セルを別のコンポーネントに置き換えることについて説明しています(たとえば、intをJTextFieldに置き換えるなど)。私の状況は少し異なります。

私は次のADTを持っています

class MyClass {
  public String title;
  public String url;
  public String path;
  public int annotations;
}

1つの列を持つカスタムテーブルセルモデルを作成しました。その列のクラスはMyClassです。次に、次のようにJPanelを返すそのクラスのセルレンダラーを作成しました。

MyClassセルレンダラー

ご覧のとおり、JPanelにはボタンが含まれています。このボタンをクリックするたびにJFrameを起動したい。何か案は?

Cell Editorを提案する場合は、その方法についてもう少し具体的に説明してください。可能であれば、いくつかの擬似コードを提供します。

ありがとうございました。

PSこの質問のタイトルにはいくつかの作業が必要だと確信しています。;)

4

3 に答える 3

9

coding.mofの返信の後、私はついにやりたいことをしました。ただし、この質問に対するより完全な回答が必要だったので、自分で回答します。

したがって、セルレンダラーはコンポーネントを描画するだけで、コンポーネント内での相互作用を許可しません。セルエディタはそうしますが。

最初、JTableのすべてのセルは、登録されたレンダラーによって返されるコンポーネントです。ただし、セルを選択すると、このコンポーネントはエディターによって返されるコンポーネントに置き換えられます。これら2つは、実際には異なるコンポーネントである可能性があります。これを利用して、ファンキーなセルを作成できると確信しています:P

とにかく、この例では、レンダラーとエディターの両方が同じコンポーネントを表示するため、両方で使用されるコンポーネントを作成します。

まず、ADTを返すTableModelを作成する必要があります。

class MyClassTableModel extends DefaultTableModel {
  List<MyClass> data;

  public MyClassTableModel(List<MyClass> data) {
    this.data = data;
  }

  public Class<?> getColumnClass(int columnIndex) { return MyClass.class; }
  public int getColumnCount() { return 1; }
  public String getColumnName(int columnIndex) { return "MyClass"; }
  public int getRowCount() { return (data == null) ? 0 : data.size(); }
  public Object getValueAt(int rowIndex, int columnIndex) { return data.get(rowIndex); }
  public boolean isCellEditable(int rowIndex, int columnIndex) { return true; }
}

次に、レンダラーとエディターの間で共有されるコンポーネントを作成します。

class MyClassCellComponent extends JPanel() {
  MyClass myClass;

  public MyClassCellComponent() {
    // initialize components (labels, buttons, etc.)
    // add action listeners
  }

  public void updateData(MyClass myClass, boolean isSelected, JTable table) {
    this.myClass = myClass;
    // update buttons, labels etc. accordingly
  }
}

isSelectedおよびtableパラメーターは、パネルの背景をレンダリングするために使用され、オプションです。レンダラーがコンポーネントを使用する方法は次のとおりです。

class MyClassCellRenderer implements TableCellRenderer {
  MyClassCellComponent panel;

  public MyClassCellRenderer() {
    panel = new MyClassCellComponent();
  }

  public Component getTableCellRendererComponent(JTable table, Object value,        boolean isSelected, boolean hasFocus, int row, int column) {
    MyClass myClass = (MyClass)value;
    panel.updateData(myClass, isSelected, table);
    return panel;
  }
}

そして、これがエディターがそれをどのように使用するかです:

class MyClassCellEditor extends AbstractCellEditor {
  MyClassCellComponent panel;
  public MyClassCellEditor() {
    panel = new MyClassCellComponent();
  }
  public Component getTableCellEditorComponent(JTable table, Object value,      boolean isSelected, int row, int column) {
    MyClass myClass = (MyClass)value;
    panel.updateData(myClass, true, table);
    return panel;
  }
  public Object getCellEditorValue() {
    return null;
  }
}

それで全部です。これで、次のようにJTableを簡単に作成できます。

JTable myClassTable = new JTable(new MyClassTableModel());
myClassTable.setDefaultRenderer(MyClass.class, new MyClassCellRenderer());
myClassTable.setDefaultEditor(MyClass.class, new MyClassCellEditor());

これで完了です。

PSレンダラーとエディターを1つのクラスに組み合わせて、AbstractCellEditorを拡張し、TableCellRendererを実装できると確信していますが、パフォーマンスについてはよくわかりません。

于 2010-08-31T08:45:47.233 に答える
5
public class MyTableCellEditor extends AbstractCellEditor implements TableCellEditor { 

JComponent pan = new JPanel();

public MyTableCellEditor () {
  pan.add(btn);
  // add all elments you need to your panel
  btn.addActionListener( /* the listener which will handle the events */ );
}

public Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int rowIndex, int vColIndex) { 
   btn.setText( /* according to row or whatever*/ );
   // set all elemnts of you panel to the according values
   // or add dynamically an action listener
   return pan;
}
public Object getCellEditorValue() { return new Void(); } 
} 

したがって、リスナーでは、行ごとに異なる方法で応答できるように、テーブルの選択を確認する必要があります。すべての要素を1つの列に保持する場合は、JButtonをすべてのコンポーネントを含むパネルに置き換えることができます。その後、JTableはすべてのイベントをそのJPanelに転送します。

于 2010-08-31T07:32:25.830 に答える
0

複数の列を持つテーブルを作成してから、ボタンを含む別の列を追加できます。Table Button Columnクラスを使用すると、これを簡単に行うことができます。

于 2010-08-31T15:27:32.770 に答える