很抱歉它是重复的 - 当我写这篇文章时,我很着急,没有时间检查。虽然我想它本来会更快,但现在我想起来了......
我一直在写一个应用程序,我正在尝试制作热键。我决定使用KeyListener
,因为这是我所知道的。但是,该课程没有响应按键。我该如何修复这个错误?如果KeyListener
有替代方法可以做同样的事情,请告诉我,最好提供一个如何运作的例子。
import java.awt.BorderLayout;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import javax.swing.*;
import panels.TabBar;
public class __mn implements KeyListener {
static JFrame disp = new JFrame("dat app");
static TabBar tabs = new TabBar();
public static void main(String[] args) {
disp.setLayout(new BorderLayout());
disp.add(tabs, BorderLayout.PAGE_START);
disp.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
disp.setSize(TabBar.PREF_WIDTH, 500);
disp.setResizable(false);
disp.setLocationRelativeTo(null);
disp.addKeyListener(new __mn());
disp.setVisible(true);
}
@Override
public void keyPressed(KeyEvent e) {
System.out.println(e.paramString());
}
//Unused
@Override public void keyReleased(KeyEvent e) {
System.out.println(e.paramString());
}
@Override public void keyTyped(KeyEvent e) {
System.out.println(e.paramString());
}
}
package panels;
import java.awt.Color;
import java.awt.FlowLayout;
import java.awt.LayoutManager;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JPanel;
//http://www.dreamincode.net/forums/topic/245148-java-key-binding-tutorial-and-demo-program/
public class TabBar extends JPanel implements ActionListener {
private static final long serialVersionUID = 1L;
public static final int NONE = -1;
public static final int INBOX = 0;
public static final int SEND_MSG = 1;
public static final int PRIVATE_CHAT = 2;
public static final int FEEDBACK = 3;
public static final int PREF_WIDTH = 425;
private static final String[] tabNames = {"Inbox", "Send a message", "Private chat", "Feedback"};
private static final JButton btnInbox = new JButton(tabNames[INBOX]);
private static final JButton btnSendMSG = new JButton(tabNames[SEND_MSG]);
private static final JButton btnPrivChat = new JButton(tabNames[PRIVATE_CHAT]);
private static final JButton btnFeedback = new JButton(tabNames[FEEDBACK]);
public int currentTab = -1;
public TabBar() {
this(new FlowLayout());
}
public TabBar(LayoutManager layout) {
super(layout);
add(btnInbox);
add(btnSendMSG);
add(btnPrivChat);
add(btnFeedback);
btnInbox.addActionListener(this);
btnSendMSG.addActionListener(this);
btnPrivChat.addActionListener(this);
btnFeedback.addActionListener(this);
setBackground(Color.BLACK);
}
@Override
public void actionPerformed(ActionEvent e) {
System.out.println(e.paramString());
if (e.getSource() == btnInbox)
currentTab = INBOX;
else if (e.getSource() == btnSendMSG)
currentTab = SEND_MSG;
else if (e.getSource() == btnPrivChat)
currentTab = PRIVATE_CHAT;
else if (e.getSource() == btnFeedback)
currentTab = FEEDBACK;
else currentTab = NONE;
}
public void hotkeyPressed(char pressed) {
pressed = Character.toLowerCase(pressed);
System.out.println("Hotkey pressed: " + pressed);
switch (pressed) {
case 'i':
setTab(INBOX);
break;
case 's':
setTab(SEND_MSG);
break;
case 'p':
setTab(PRIVATE_CHAT);
break;
case 'f':
setTab(FEEDBACK);
break;
default:
break;
}
}
private void setTab(int tab) {
System.out.println("Somthing pressed! tab=" + tab);
currentTab = tab;
switch (tab) {
case INBOX:
btnInbox.requestFocusInWindow();
}
}
}
答案 0 :(得分:4)
我该如何修复这个错误?
不是真正的错误,不兼容。
如果KeyListener有替代方法可以做同样的事情, 请让我知道,最好提供一个例子 工作
不要将KeyListener
/ KeyAdapter
用于Swing组件,因为存在焦点问题,可以通过在组件可见后调用组件上的requestFocusInWindow()
来确保它具有焦点并且当然,如果组件不像<{1}}一样可聚焦,则必须调用setFoucsable(true);
。
Swing组件应该使用KeyBinding
s,它可以通过在添加了JLabel
的组件上自动调用setFocusable(true)
来克服上述问题。
这是一个小例子:
KeyBinding
您可以使用您要添加void addKeyBinding(JComponent jc) {
jc.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).put(KeyStroke.getKeyStroke(KeyEvent.VK_A, 0, false), "A pressed");
jc.getActionMap().put("esc pressed", new AbstractAction() {
@Override
public void actionPerformed(ActionEvent ae) {
System.out.println("A pressed");
}
});
jc.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).put(KeyStroke.getKeyStroke(KeyEvent.VK_A, 0, true), "A released");
jc.getActionMap().put("A released", new AbstractAction() {
@Override
public void actionPerformed(ActionEvent ae) {
System.out.println("A released");
}
});
}
的{{1}}即JComponent
等实例来调用此方法:
JPanel
有关代码的其他建议:
始终通过Keybinding
阻止<{1}}在JPanel p=new JPanel();
addKeyBinding(p);
创建Swing组件
除非此类仅用作Event Dispatch Thread
,否则您不要在类本身上实现SwingUtilities.invokeXXX
Listener
,或者您想要将实现类/ ActionListener
方法暴露给其他类。
答案 1 :(得分:2)
JFrame由许多不同的组件组成,因此不是可以集中注意力的。没有焦点,它无法接收关键事件。有很多解决方案。我只会建议这个:
Unresponsive KeyListener for JFrame
我会建议你google“jyp java上的keylistener”来查找更多信息。就像我说的,有很多方法可以解决这个问题。