java - 如何创建每行具有不同按钮的jtable

标签 java swing jtable

我已经尝试过 http://java-swing-tips.blogspot.com/2009/10/multiple-jbuttons-in-jtable-cell.html 的教程生成下表。

enter image description here

现在,我需要创建一个表格,每行包含不同的按钮。请帮助我。

table pattern

最佳答案

我猜想 EnumSet是您正在寻找的:

enter image description here

import java.awt.*;
import java.awt.event.*;
import java.util.*;
import java.util.List;
import javax.swing.*;
import javax.swing.table.*;

public final class EnumSetTest {
  private JComponent makeUI() {
    String[] columnNames = {"REPORT ID", "ACTION"};
    Object[][] data = {
      {"Report1", EnumSet.of(Actions.PRINT)},
      {"Report2", EnumSet.of(Actions.PRINT, Actions.EDIT)},
      {"Report3", EnumSet.allOf(Actions.class)},
      {"Report4", EnumSet.of(Actions.PRINT)}
    };
    DefaultTableModel model = new DefaultTableModel(data, columnNames) {
      @Override public Class<?> getColumnClass(int column) {
        return getValueAt(0, column).getClass();
      }
    };
    JTable table = new JTable(model);
    table.setRowHeight(36);
    TableColumn column = table.getColumnModel().getColumn(1);
    column.setCellRenderer(new ButtonsRenderer());
    column.setCellEditor(new ButtonsEditor(table));
    return new JScrollPane(table);
  }
  public static void main(String[] args) {
    EventQueue.invokeLater(new Runnable() {
      @Override public void run() {
        createAndShowGUI();
      }
    });
  }
  public static void createAndShowGUI() {
    JFrame f = new JFrame();
    f.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
    f.getContentPane().add(new EnumSetTest().makeUI());
    f.setSize(320, 240);
    f.setLocationRelativeTo(null);
    f.setVisible(true);
  }
}

enum Actions { PRINT, EDIT; }

class ButtonsPanel extends JPanel {
  public final List<JButton> buttons = new ArrayList<>();
  public ButtonsPanel() {
    super(new FlowLayout(FlowLayout.LEFT));
    setOpaque(true);
    for (Actions a : Actions.values()) {
      JButton b = new JButton(a.toString());
      b.setFocusable(false);
      b.setRolloverEnabled(false);
      add(b);
      buttons.add(b);
    }
  }
  protected void updateButtons(Object value) {
    if (value instanceof EnumSet) {
      EnumSet ea = (EnumSet) value;
      removeAll();
      if (ea.contains(Actions.PRINT)) {
        add(buttons.get(0));
      }
      if (ea.contains(Actions.EDIT)) {
        add(buttons.get(1));
      }
    }
  }
}

class ButtonsRenderer implements TableCellRenderer {
  private final ButtonsPanel panel = new ButtonsPanel();
  @Override public Component getTableCellRendererComponent(
      JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) {
    panel.setBackground(isSelected ? table.getSelectionBackground() : table.getBackground());
    panel.updateButtons(value);
    return panel;
  }
}

class PrintAction extends AbstractAction {
  private final JTable table;
  public PrintAction(JTable table) {
    super(Actions.PRINT.toString());
    this.table = table;
  }
  @Override public void actionPerformed(ActionEvent e) {
    JOptionPane.showMessageDialog(table, "Printing");
  }
}

class EditAction extends AbstractAction {
  private final JTable table;
  public EditAction(JTable table) {
    super(Actions.EDIT.toString());
    this.table = table;
  }
  @Override public void actionPerformed(ActionEvent e) {
    int row = table.convertRowIndexToModel(table.getEditingRow());
    Object o = table.getModel().getValueAt(row, 0);
    JOptionPane.showMessageDialog(table, "Editing: " + o);
  }
}

class ButtonsEditor extends AbstractCellEditor implements TableCellEditor {
  private final ButtonsPanel panel = new ButtonsPanel();
  private final JTable table;
  private Object o;
  private class EditingStopHandler extends MouseAdapter implements ActionListener {
    @Override public void mousePressed(MouseEvent e) {
      Object o = e.getSource();
      if (o instanceof TableCellEditor) {
        actionPerformed(null);
      } else if (o instanceof JButton) {
        ButtonModel m = ((JButton) e.getComponent()).getModel();
        if (m.isPressed() && table.isRowSelected(table.getEditingRow()) && e.isControlDown()) {
          panel.setBackground(table.getBackground());
        }
      }
    }
    @Override public void actionPerformed(ActionEvent e) {
      EventQueue.invokeLater(new Runnable() {
        @Override public void run() {
          fireEditingStopped();
        }
      });
    }
  }
  public ButtonsEditor(JTable table) {
    super();
    this.table = table;
    panel.buttons.get(0).setAction(new PrintAction(table));
    panel.buttons.get(1).setAction(new EditAction(table));

    EditingStopHandler handler = new EditingStopHandler();
    for (JButton b : panel.buttons) {
      b.addMouseListener(handler);
      b.addActionListener(handler);
    }
    panel.addMouseListener(handler);
  }
  @Override public Component getTableCellEditorComponent(
      JTable table, Object value, boolean isSelected, int row, int column) {
    panel.setBackground(table.getSelectionBackground());
    panel.updateButtons(value);
    o = value;
    return panel;
  }
  @Override public Object getCellEditorValue() {
    return o;
  }
}

关于java - 如何创建每行具有不同按钮的jtable,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24025560/

相关文章:

java - 如何更新 JTable View

java - 为 JTable 指定列特定的 TableCellRenderer

java - 在java JFrame中的特定网格空间内移动对象可能使用GridBagLayout吗?

java - 为什么JFrame布局不是我设置的布局?

java - FEST:当单元格位于带有 CellRenderPane 的 JTable 下时检索单元格值

java - 在非 AWT 线程中更新 AbstractTableModel 中的数据的最佳实践

java - 从 Android 接收 Base64 编码的字符串到 C# 应用程序

java - 这里发生了什么 : sum += i++;?

java - 仅出于履行契约(Contract)的目的而在方法签名中包含 args 是否是常见的做法

java - 将对象列表从父类转换为各个子类的正确方法