Как я могу дать указание моему компоненту Swing захватить фокус прямо сейчас ?requestFocus()
, кажется, не отправляется мгновенно.
В идеале, я хотел бы, чтобы (бег от EDT):
textInput.requestFocusInWindow();
System.out.println(textInput.hasFocus());
Для печати true
.
Ниже SSCCE.Примечания / требования:
- Таблица перемещается с помощью клавиатуры.Столбец C2 имеет составной редактор.
- Когда я набираю букву в столбце C2, начинается редактирование.Текстовый компонент внутри составного редактора получает фокус.Нужно набрать письмо, которое запустил редактор.Реализация этого пункта отмечена комментариями с надписью «Уловка».
- Текстовое поле - сторонний редактор, у которого слушатель фокуса вмешивается в мой код.Здесь он имитируется как
selectAll()
.
. В настоящее время порядок отправки такой: введите букву в текстовый компонент, затем отправьте фокус слушателям.Затем следующие буквы отправляются правильно, потому что это текстовое поле, которое имеет фокус.
Мне нужно, чтобы оно установило фокус на текстовом компоненте, направило слушателей фокуса и затем передало ему ключевое событие.
public class JTableIssue extends JFrame {
public JTableIssue() {
JTable table = new JTable(new Object[][] {
{ "Apple", "Orange", "Strawberry" },
{ "Pineapple", "Orange", "Zergz" } }, new Object[] { "C1",
"C2", "C3" });
table.getColumn("C2").setCellEditor(new MyEditor());
add(new JScrollPane(table));
pack();
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
public static void main(String[] args) {
new JTableIssue().setVisible(true);
}
}
class MyEditor extends AbstractCellEditor implements TableCellEditor {
MyTextField textField = new MyTextField();
JPanel panel;
MyEditor() {
panel = new JPanel(new BorderLayout()){
// Trick: Pass all key typed to text field
@Override
protected boolean processKeyBinding(KeyStroke ks, KeyEvent e,
int condition, boolean pressed) {
if (ks.getKeyEventType() == KeyEvent.KEY_TYPED) {
textField.processKeyBinding(ks, e, condition, pressed);
}
return super.processKeyBinding(ks, e, condition, pressed);
}
};
textField.addFocusListener(new FocusAdapter() {
@Override
public void focusGained(FocusEvent e) {
textField.selectAll();
}
});
panel.add(textField, BorderLayout.CENTER);
// Trick: Pass focus to text field when editor is added to table
panel.addAncestorListener(new AncestorListener() {
public void ancestorRemoved(AncestorEvent event) {
}
public void ancestorMoved(AncestorEvent event) {
}
public void ancestorAdded(AncestorEvent event) {
textField.requestFocus();
}
});
}
public Object getCellEditorValue() {
return textField.getText();
}
public Component getTableCellEditorComponent(JTable table, Object value,
boolean isSelected, int row, int column) {
textField.setText(value.toString());
return panel;
}
}
class MyTextField extends JTextField {
// Trick: "public"
@Override
public boolean processKeyBinding(javax.swing.KeyStroke ks,
java.awt.event.KeyEvent e, int condition, boolean pressed) {
return super.processKeyBinding(ks, e, condition, pressed);
};
}