我有一个JTable
,其中一个列(第1列)是一个JComboBox,它允许从列表中进行选项,并可以在其中输入新的选项。 MWE:
import javax.swing.DefaultCellEditor;
import javax.swing.JComboBox;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.table.TableColumn;
import java.awt.Dimension;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Arrays;
import java.util.HashSet;
public class ComboTableDemo extends JPanel {
public ComboTableDemo() {
super(new GridLayout(1,0));
final String[] headings = {"Name", "Option"};
final String string1 = "Foo";
final String string2 = "Bar";
Object[][] data = {
{"Albert", string1},
{"Bob", null},
{"Clare", null},
{"David", null}
};
final JTable table = new JTable(data, headings);
table.setPreferredScrollableViewportSize(new Dimension(300, 100));
table.setFillsViewportHeight(true);
final String[] optionsInit = new String[] {string1, string2};
HashSet<String> options = new HashSet<String>(Arrays.asList(optionsInit));
JComboBox<String> optionsCombo = new JComboBox<String>(optionsInit);
optionsCombo.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent ev) {
String newSelection = (String)optionsCombo.getSelectedItem();
if(!options.contains(newSelection)) {
options.add(newSelection);
optionsCombo.addItem(newSelection);
}
}
});
optionsCombo.setEditable(true);
TableColumn column = table.getColumnModel().getColumn(1);
column.setCellEditor(new DefaultCellEditor(optionsCombo));
add(new JScrollPane(table));
}
public static void main(String[] args) {
javax.swing.SwingUtilities.invokeLater(new Runnable() {
public void run() {
JFrame frame = new JFrame("ComboTableDemo");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
ComboTableDemo pane = new ComboTableDemo();
pane.setOpaque(true);
frame.setContentPane(pane);
frame.pack();
frame.setVisible(true);
}
});
}
}
在表中,用户可以并且应该为空条目输入值并不明显,因此我想添加占位符文本以使其清楚。我已经elsewhere看到,ListCellRenderer
可以为自定义setRenderer
提供ComboBoxEditor
,如果组合是不可编辑的,则组合为可编辑的(如tutorial中所述),看来必须使用setEditor
提供{{1}}。为此是否有一个简单的实现,或者甚至是达到相同目的的更好方法?
答案 0 :(得分:0)
实际上,JTable
中的输入组件具有特殊情况,因为它们仅在单元格被编辑时才处于活动状态。因此,除了设置编辑器以控制值的编辑方式外,还需要更改渲染器以控制如何显示所选值,
// As before:
TableColumn column = table.getColumnModel().getColumn(1);
column.setCellEditor(new DefaultCellEditor(optionsCombo));
// Additional line to set renderer:
column.setCellRenderer(new PlaceholderRenderer("<choose or add option>"));
此处PlaceholderRenderer
应该是TableCellRenderer
的实现,当未选择任何值时,该实现将显示占位符字符串。例如:
import java.awt.Component;
import javax.swing.JTable;
import javax.swing.table.DefaultTableCellRenderer;
public class PlaceholderRenderer extends DefaultTableCellRenderer {
final private String placeholder;
public PlaceholderRenderer(String placeholder) {
super();
this.placeholder = placeholder;
}
@Override
public Component getTableCellRendererComponent(JTable table,
Object value,
boolean isSelected,
boolean hasFocus,
int row,
int column) {
if ((value == null) || (value.equals(""))) {
return super.getTableCellRendererComponent(table, this.placeholder, isSelected, hasFocus, row, column);
} else {
return super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
}
}
}