gpt4 book ai didi

如果我添加 JButton,Java FocusListener 和 KeyListener 将不起作用

转载 作者:行者123 更新时间:2023-11-30 01:43:38 24 4
gpt4 key购买 nike

我有两个实现 KeyListener 和 FocusListener 接口(interface)的类。两者都不起作用,但如果我不通过注释或删除以下内容来添加 JButton:add(whiteJButton),那么它们就可以工作。有人可以向我解释为什么会发生这种情况吗?提前致谢。

import java.awt.Color;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class JFrames {

public static void main(String[] args) {

JFrame myJFrame = new JFrame("MyJFrame");

myJFrame.setBounds(400, 400, 500, 500);
myJFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

MyJPanel myJPanel = new MyJPanel();
myJFrame.add(myJPanel);

// Doesn't work
myJFrame.addKeyListener(new MyKeyListener());
// Doesn't work
myJFrame.addFocusListener(new MyFocusListener());

myJFrame.setVisible(true);
}

static class MyJPanel extends JPanel {

public MyJPanel() {

JButton whiteJButton = new JButton("WHITE");
add(whiteJButton);
whiteJButton.addActionListener(new ActionListener() {

@Override
public void actionPerformed(ActionEvent e) {
setBackground(Color.WHITE);
}
});
}
}
}

class MyKeyListener implements KeyListener {

@Override
public void keyTyped(KeyEvent e) {
System.out.println("keyTyped: " + e.getKeyChar());
}

@Override
public void keyPressed(KeyEvent e) {
System.out.println("keyPressed: " + e.getKeyChar());
}

@Override
public void keyReleased(KeyEvent e) {
System.out.println("keyReleased: " + e.getKeyChar());
}

}

class MyFocusListener implements FocusListener {

@Override
public void focusGained(FocusEvent e) {
System.out.println("focusGained");
}

@Override
public void focusLost(FocusEvent e) {
System.out.println("focusLost");
}

}

最佳答案

问题在于该按钮从 JFrame 窃取了焦点,从而阻止焦点监听器工作(焦点已经消失)。如果您绝对需要使用 KeyListener,则一些解决方案是拼凑而成,包括使 JButton 不可聚焦:whiteJButton.setFocusable(false);,但如果您这样做,则需要为 执行此操作添加了所有组件。是的,您可以按照其他答案的建议请求焦点,但它应该是 requestFocusInWindw(),而不是 requestFocus() (许多类似的问题解释了为什么会这样)。如果你这样做并且组件仍然可以聚焦,那么如果组件获得焦点,整个事情就会崩溃——这不好。

更好(根据评论)是使用 Key Bindings如果您使用正确的输入映射,则不需要焦点即可工作。请注意,键绑定(bind)是 Swing 本身捕获组件击键的方式,因此使用它会遵循 Swing 的一般结构和契约。键绑定(bind)的问题是您必须绑定(bind)要捕获的每个键,但您可以使用 for 循环来协助完成此操作。

另一个解决方案是使用 KeyEventDispatcher 来进行键盘焦点管理器:

KeyboardFocusManager.getCurrentKeyboardFocusManager().addKeyEventDispatcher(new KeyEventDispatcher() {
@Override
public boolean dispatchKeyEvent(KeyEvent e) {
// code goes here
return false;
}
});

使用键绑定(bind)的示例:

import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import javax.swing.*;

@SuppressWarnings("serial")
public class KeyboardFun extends JPanel {
private InputMap inputMap = getInputMap(WHEN_IN_FOCUSED_WINDOW);
private ActionMap actionMap = getActionMap();

public KeyboardFun() {
setBorder(BorderFactory.createEmptyBorder(3, 3, 3, 3));
setLayout(new GridLayout(0, 8, 3, 3));
for (char c = 'A'; c <= 'Z'; c++) {
final String text = String.valueOf(c);
JButton button = new JButton(text);
button.addActionListener(e -> {System.out.println("Key pressed: " + text);});
add(button);
setBinding(c, button);
}
}

private void setBinding(char c, final JButton button) {
KeyStroke keyStroke = KeyStroke.getKeyStroke(Character.toLowerCase(c));
inputMap.put(keyStroke, keyStroke.toString());
actionMap.put(keyStroke.toString(), new AbstractAction() {

@Override
public void actionPerformed(ActionEvent e) {
button.doClick();
}
});
}

private static void createAndShowGui() {
KeyboardFun mainPanel = new KeyboardFun();

JFrame frame = new JFrame("KeyboardFun");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.getContentPane().add(mainPanel);
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}

public static void main(String[] args) {
SwingUtilities.invokeLater(() -> createAndShowGui());
}
}

关于如果我添加 JButton,Java FocusListener 和 KeyListener 将不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59018108/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com