[英]Usability features for JComboBox within JTable
I'm trying to build a table which includes JComboBoxes as both the renderer and editor components. 我正在尝试建立一个包含JComboBoxes作为渲染器和编辑器组件的表。 This mostly works fine, however there are two things I can't seem to solve.
这通常可以正常工作,但是有两件事我似乎无法解决。
Regarding 1, the editable combo should place focus within the embedded text field, the fixed combo should allow the down arrow to open the list of options. 关于1,可编辑组合应该将焦点放在嵌入式文本字段内,固定组合应允许向下箭头打开选项列表。
Regarding 2, I find that this sometimes works depending on what other cell is currently active, but other times I have to double click. 关于2,我发现这有时会起作用,这取决于当前处于活动状态的其他单元格,但是有时我必须双击。 I cannot make this behaviour consistent.
我无法使这种行为保持一致。
For convenience I have included a clear example which (I believe) uses the recommended approach for embedding JComboBoxes within Jtables. 为了方便起见,我提供了一个明确的示例(我相信),该示例使用推荐的方法将JComboBoxes嵌入Jtables中。
Thank you for constructive advice. 感谢您的建设性建议。
import java.awt.Component;
import java.util.*;
import javax.swing.*;
import javax.swing.table.*;
public class TableCombos
{
public static void main(String[] args)
{
JFrame frame = new JFrame("Frame");
frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);
AbstractTableModel model = new DefaultTableModel()
{
String[] columnHeaders = new String[]{"label", "combo-edit", "combo-fixed"};
Class<?>[] columnClasses = new Class<?>[]{String.class, Double.class, Double.class};
List<Object[]> data = new ArrayList<>();
{
data.add(new Object[]{"row 1", 1.0d, 2.0d});
data.add(new Object[]{"row 2", 2.0d, 3.0d});
}
@Override
public int getColumnCount()
{
return columnHeaders.length;
}
@Override
public boolean isCellEditable(int row, int column)
{
return column != 0;
}
@Override
public int getRowCount()
{
if (data == null) // race condition
return 0;
return data.size();
}
@Override
public Object getValueAt(int row, int column)
{
return data.get(row)[column];
}
@Override
public void setValueAt(Object aValue, int row, int column)
{
data.get(row)[column] = aValue;
}
@Override
public Class<?> getColumnClass(int column)
{
return columnClasses[column];
}
@Override
public String getColumnName(int column)
{
return columnHeaders[column];
}
};
JTable table = new JTable(model);
table.setSurrendersFocusOnKeystroke(true);
TableColumn c1 = table.getColumnModel().getColumn(1);
TableColumn c2 = table.getColumnModel().getColumn(2);
JComboBox<Double> editorComboEditable = new JComboBox<>(new Double[]{1.0d, 2.0d, 3.0d});
editorComboEditable.setEditable(true);
c1.setCellEditor(new DefaultCellEditor(editorComboEditable));
c2.setCellEditor(new DefaultCellEditor(new JComboBox<>(new Double[]{1.0d, 2.0d, 3.0d})));
final JComboBox<Double> rendererComboEditable = new JComboBox<>(new Double[]{1.0d, 2.0d, 3.0d});
rendererComboEditable.setEditable(true);
final JComboBox<Double> rendererComboFixed = new JComboBox<>(new Double[]{1.0d, 2.0d, 3.0d});
c1.setCellRenderer(new TableCellRenderer()
{
@Override
public Component getTableCellRendererComponent(JTable t, Object value, boolean isSelected, boolean hasFocus, int row, int column)
{
rendererComboEditable.setSelectedItem(value);
return rendererComboEditable;
}
});
c2.setCellRenderer(new TableCellRenderer()
{
@Override
public Component getTableCellRendererComponent(JTable t, Object value, boolean isSelected, boolean hasFocus, int row, int column)
{
rendererComboFixed.setSelectedItem(value);
return rendererComboFixed;
}
});
frame.getContentPane().add(new JScrollPane(table));
frame.pack();
frame.setVisible(true);
}
}
Both of your issues be resolved by overriding the DefaultCellEditor#isCellEditable
method and returning true
通过重写
DefaultCellEditor#isCellEditable
方法并返回true
可以解决两个问题
You may need to set JTable#setSurrendersFocusOnKeystroke
to true as well 您可能还需要将
JTable#setSurrendersFocusOnKeystroke
设置为true
Update 更新资料
The short answer is "It's messy". 简短的回答是“很乱”。 The long answer is "it's very messy"
长答案是“这很混乱”
I did a "continuos editing" process some time back. 不久前,我做了一个“持续编辑”过程。 Basically, I overrode the Enter and Tab key bindings.
基本上,我覆盖了Enter和Tab键的绑定。
What I'd did was basically stop any active cell editor, take note of the current cell and then tried to finding the next editable cell, looping back around to the start (cell 0x0) if required. 我所做的基本上是停止任何活动的单元格编辑器,记下当前单元格,然后尝试查找下一个可编辑的单元格,并根据需要循环回到起始位置(单元格0x0)。
When I found a editable cell, I called JTable#esitCellAt
to start editing the cell. 找到可编辑单元格后,我调用了
JTable#esitCellAt
开始编辑该单元格。
To get the popup to be visible when the cell starts editing, you will need to override the addNotify
method of the JComboBox
and, using SwingUtilities#invokeLater
, set the popup visible 为了使该弹出窗口在单元格开始编辑时可见,您将需要重写
JComboBox
的addNotify
方法,并使用SwingUtilities#invokeLater
将弹出窗口设置为可见
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.