一旦按下按钮,Java 键事件就不会执行

发布于 2025-01-02 10:26:36 字数 3145 浏览 6 评论 0原文

您好,希望有人能告诉我我的关键事件做错了什么。

我正在使用卡片布局来浏览我的两个 JPanels atm。为此,我使用操作事件和关键事件。当按下按钮时,动作事件将在 JPanel 之间切换,而当按下按键时,按键事件将隐藏按钮。按键事件一切都很好,它做了我想要的事情(在其中一个面板上调用一个方法来设置放置在其中的按钮的边界,例如:button.setBounds(-1, -1, 150, 40);但是当 下面是我的代码,为了简单起见,我删除了面板的不相关部分,就像它们应该做的那样。

我按下任何按钮,按键事件都不会响应,尽管我按下的按钮上没有任何事件, 请告诉我是否我需要提供更多线索或者更多地编辑代码,我会尽力使代码更清晰。

public class PanelContainer extends JPanel implements ActionListener, KeyListener{
    GamePanel game = new GamePanel();
    MainMenuPanel mainMenu = new MainMenuPanel();
    CardLayout cards = new CardLayout();
    public PanelContainer(){
        setLayout(cards);
        this.setFocusable(true);
        this.addKeyListener(this);
        mainMenu.newGameButton.addActionListener(this);
        add(mainMenu, "Card1");
        add(game, "Card2");
    }
    @Override
    public void actionPerformed(ActionEvent aevt){
        cards.show(this, "Card2");
        game.action();
    }
    @Override
    public void keyTyped(KeyEvent kevt){

    }
    @Override
    public void keyPressed(KeyEvent kevt){

    }
    @Override
    public void keyReleased(KeyEvent kevt){
        if(kevt.getKeyCode() == KeyEvent.VK_ESCAPE || kevt.getKeyChar() == 'O' ||    kevt.getKeyChar() == 'o'){
            game.shw(); //shw() is a method inside GamePanel that sets the bounds of the buttons
        }
        else if (kevt.getKeyChar() == 'h' || kevt.getKeyChar() == 'H'){game.hid();}
    }
}





public class MainMenuPanel extends JPanel
{
    private URL workingDir = this.getClass().getResource("imgresources/brick_wall.png") ;
    private ImageIcon icon = new ImageIcon(workingDir) ;
    private Image img = icon.getImage();
    //create and initiate buttons;
    JButton newGameButton = new JButton("New Game"); 
    JButton highScoreButton = new JButton("High Scores");
    JButton controlsButton = new JButton("Controls");
    Point[] points = new Point[1000];

    public MainMenuPanel(){
        add(newGameButton);
        add(highScoreButton);
        add(controlsButton);
        setPoints();
    }

    public void setButtonsBounds(){
        newGameButton.setBounds(450, 200, 200, 40);
        highScoreButton.setBounds(450, 250, 200, 40);
        controlsButton.setBounds(450, 300, 200, 40);
    }

    @Override
    public void paintComponent(Graphics g){
        try{
            super.paintComponent(g);
            Graphics2D d2 = (Graphics2D) g;
            d2.setColor(new Color(0, 0, 0));
            d2.fillRect(0, 0, this.getWidth(), this.getHeight());

            setButtonsBounds();
            for(int i=0; i<275; i++){
                d2.drawImage(img, points[i].x +200, points[i].y, this);
            }
        }catch(Exception e){}
    }
}





public class GamePanel extends JPanel implements Runnable{
    JButton button = new JButton("Main Menu");
    JButton button2 = new JButton("Exit Game");
    void shw(){
       add(button);
       add(button2);
       button.setBounds(400, 200, 150, 20);
       button2.setBounds(400, 240, 150, 20);

    }
    void hid(){
       button.setBounds(1, 1, 150, 20);
       button2.setBounds(1, 40, 150, 20);
    }
}

Hi hope someone can tell me what I am doing wrong with my Key Event.

I am using a Card Layout to navigate through two of my JPanels atm. To do so I use Action Events as well as Key Events. The action events will toggle between JPanels when a button is pressed while the key events will hide away the buttons when a key is pressed. All good with the key events, it does what I want (call a method on one of the panels to set the bounds of the buttons placed inside it eq: button.setBounds(-1, -1, 150, 40); but when I press any of the buttons the key event wont respond despite not having any event on the buttons that I press. Below is my code, for simplicity I removed the non relevant parts of the panels like what they are meant to do.

Thanks in advance and please let me know if I need to provide more clues or to edit the code more, I will try my best to make the code clearer.

public class PanelContainer extends JPanel implements ActionListener, KeyListener{
    GamePanel game = new GamePanel();
    MainMenuPanel mainMenu = new MainMenuPanel();
    CardLayout cards = new CardLayout();
    public PanelContainer(){
        setLayout(cards);
        this.setFocusable(true);
        this.addKeyListener(this);
        mainMenu.newGameButton.addActionListener(this);
        add(mainMenu, "Card1");
        add(game, "Card2");
    }
    @Override
    public void actionPerformed(ActionEvent aevt){
        cards.show(this, "Card2");
        game.action();
    }
    @Override
    public void keyTyped(KeyEvent kevt){

    }
    @Override
    public void keyPressed(KeyEvent kevt){

    }
    @Override
    public void keyReleased(KeyEvent kevt){
        if(kevt.getKeyCode() == KeyEvent.VK_ESCAPE || kevt.getKeyChar() == 'O' ||    kevt.getKeyChar() == 'o'){
            game.shw(); //shw() is a method inside GamePanel that sets the bounds of the buttons
        }
        else if (kevt.getKeyChar() == 'h' || kevt.getKeyChar() == 'H'){game.hid();}
    }
}





public class MainMenuPanel extends JPanel
{
    private URL workingDir = this.getClass().getResource("imgresources/brick_wall.png") ;
    private ImageIcon icon = new ImageIcon(workingDir) ;
    private Image img = icon.getImage();
    //create and initiate buttons;
    JButton newGameButton = new JButton("New Game"); 
    JButton highScoreButton = new JButton("High Scores");
    JButton controlsButton = new JButton("Controls");
    Point[] points = new Point[1000];

    public MainMenuPanel(){
        add(newGameButton);
        add(highScoreButton);
        add(controlsButton);
        setPoints();
    }

    public void setButtonsBounds(){
        newGameButton.setBounds(450, 200, 200, 40);
        highScoreButton.setBounds(450, 250, 200, 40);
        controlsButton.setBounds(450, 300, 200, 40);
    }

    @Override
    public void paintComponent(Graphics g){
        try{
            super.paintComponent(g);
            Graphics2D d2 = (Graphics2D) g;
            d2.setColor(new Color(0, 0, 0));
            d2.fillRect(0, 0, this.getWidth(), this.getHeight());

            setButtonsBounds();
            for(int i=0; i<275; i++){
                d2.drawImage(img, points[i].x +200, points[i].y, this);
            }
        }catch(Exception e){}
    }
}





public class GamePanel extends JPanel implements Runnable{
    JButton button = new JButton("Main Menu");
    JButton button2 = new JButton("Exit Game");
    void shw(){
       add(button);
       add(button2);
       button.setBounds(400, 200, 150, 20);
       button2.setBounds(400, 240, 150, 20);

    }
    void hid(){
       button.setBounds(1, 1, 150, 20);
       button2.setBounds(1, 40, 150, 20);
    }
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

子栖 2025-01-09 10:26:36

这是一个焦点问题。使用键绑定而不是 KeyListener,这样您就不必担心这个问题(并且还有其他好处 - 请检查 按键绑定教程了解详细信息)。

这是我的 SSCCE,它演示了我正在谈论的内容。请注意,KeyListener 和键绑定都会起作用,直到您按下按钮,然后只有绑定才起作​​用:

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

public class KeyBindingsEg {
   private static void createAndShowGui() {
      PanelContainer mainPanel = new PanelContainer();

      JFrame frame = new JFrame("KeyBindingsEg");
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
      frame.getContentPane().add(mainPanel);
      frame.pack();
      frame.setLocationByPlatform(true);
      frame.setVisible(true);
   }

   public static void main(String[] args) {
      SwingUtilities.invokeLater(new Runnable() {
         public void run() {
            createAndShowGui();
         }
      });
   }
}

@SuppressWarnings("serial")
class PanelContainer extends JPanel {

   public PanelContainer() {
      this.setFocusable(true);
      this.addKeyListener(new MyKeyListener());
      JButton newGameButton = new JButton("New Game");
      newGameButton.addActionListener(new MyActionListener());
      add(newGameButton);
      setKeyBindings();
   }

   private void setKeyBindings() {
      Action hideAction = new BindingAction(BindingAction.HIDE);
      Action showAction = new BindingAction(BindingAction.SHOW);
      int condition = JComponent.WHEN_IN_FOCUSED_WINDOW;
      InputMap inputMap = getInputMap(condition);
      ActionMap actionMap = getActionMap();

      actionMap.put(BindingAction.HIDE, hideAction);
      inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_H, 0), BindingAction.HIDE);
      inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_H, KeyEvent.SHIFT_DOWN_MASK),
            BindingAction.HIDE);

      int[] showKeys = { KeyEvent.VK_O, KeyEvent.VK_ESCAPE };
      actionMap.put(BindingAction.SHOW, showAction);
      for (int key : showKeys) {
         inputMap.put(KeyStroke.getKeyStroke(key, 0), BindingAction.SHOW);
         inputMap.put(KeyStroke.getKeyStroke(key, KeyEvent.SHIFT_DOWN_MASK),
               BindingAction.SHOW);
      }

   }

   private class MyActionListener implements ActionListener {
      @Override
      public void actionPerformed(ActionEvent aevt) {
         System.out.println("button pressed");
      }
   }

   private class MyKeyListener extends KeyAdapter {
      public void keyReleased(KeyEvent kevt) {
         if (kevt.getKeyCode() == KeyEvent.VK_ESCAPE
               || kevt.getKeyChar() == 'O' || kevt.getKeyChar() == 'o') {
            System.out.println("KeyListener: show");
         } else if (kevt.getKeyChar() == 'h' || kevt.getKeyChar() == 'H') {
            System.out.println("KeyListener: hide");
         }
      }
   }

   private class BindingAction extends AbstractAction {
      public static final String HIDE = "Hide";
      public static final String SHOW = "Show";

      public BindingAction(String text) {
         super(text);
         putValue(ACTION_COMMAND_KEY, text);
      }

      @Override
      public void actionPerformed(ActionEvent evt) {
         String actionCommand = evt.getActionCommand();
         if (actionCommand.equals(HIDE)) {
            System.out.println("key bindings: hide");
         } else if (actionCommand.equals(SHOW)) {
            System.out.println("key bindings: show");
         }
      }
   }
}

It's a focus issue. Use Key Bindings instead of a KeyListener so you don't have to worry about this issue (and for other benefits as well -- check the Key Bindings tutorial for details).

Here's my SSCCE that demonstrates what I'm talking about. Note that both KeyListener and key bindings work until you press a button, and then only bindings work:

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

public class KeyBindingsEg {
   private static void createAndShowGui() {
      PanelContainer mainPanel = new PanelContainer();

      JFrame frame = new JFrame("KeyBindingsEg");
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
      frame.getContentPane().add(mainPanel);
      frame.pack();
      frame.setLocationByPlatform(true);
      frame.setVisible(true);
   }

   public static void main(String[] args) {
      SwingUtilities.invokeLater(new Runnable() {
         public void run() {
            createAndShowGui();
         }
      });
   }
}

@SuppressWarnings("serial")
class PanelContainer extends JPanel {

   public PanelContainer() {
      this.setFocusable(true);
      this.addKeyListener(new MyKeyListener());
      JButton newGameButton = new JButton("New Game");
      newGameButton.addActionListener(new MyActionListener());
      add(newGameButton);
      setKeyBindings();
   }

   private void setKeyBindings() {
      Action hideAction = new BindingAction(BindingAction.HIDE);
      Action showAction = new BindingAction(BindingAction.SHOW);
      int condition = JComponent.WHEN_IN_FOCUSED_WINDOW;
      InputMap inputMap = getInputMap(condition);
      ActionMap actionMap = getActionMap();

      actionMap.put(BindingAction.HIDE, hideAction);
      inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_H, 0), BindingAction.HIDE);
      inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_H, KeyEvent.SHIFT_DOWN_MASK),
            BindingAction.HIDE);

      int[] showKeys = { KeyEvent.VK_O, KeyEvent.VK_ESCAPE };
      actionMap.put(BindingAction.SHOW, showAction);
      for (int key : showKeys) {
         inputMap.put(KeyStroke.getKeyStroke(key, 0), BindingAction.SHOW);
         inputMap.put(KeyStroke.getKeyStroke(key, KeyEvent.SHIFT_DOWN_MASK),
               BindingAction.SHOW);
      }

   }

   private class MyActionListener implements ActionListener {
      @Override
      public void actionPerformed(ActionEvent aevt) {
         System.out.println("button pressed");
      }
   }

   private class MyKeyListener extends KeyAdapter {
      public void keyReleased(KeyEvent kevt) {
         if (kevt.getKeyCode() == KeyEvent.VK_ESCAPE
               || kevt.getKeyChar() == 'O' || kevt.getKeyChar() == 'o') {
            System.out.println("KeyListener: show");
         } else if (kevt.getKeyChar() == 'h' || kevt.getKeyChar() == 'H') {
            System.out.println("KeyListener: hide");
         }
      }
   }

   private class BindingAction extends AbstractAction {
      public static final String HIDE = "Hide";
      public static final String SHOW = "Show";

      public BindingAction(String text) {
         super(text);
         putValue(ACTION_COMMAND_KEY, text);
      }

      @Override
      public void actionPerformed(ActionEvent evt) {
         String actionCommand = evt.getActionCommand();
         if (actionCommand.equals(HIDE)) {
            System.out.println("key bindings: hide");
         } else if (actionCommand.equals(SHOW)) {
            System.out.println("key bindings: show");
         }
      }
   }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文