2013-08-01 2 views
7

Я пытаюсь сделать привязки клавиш в Java на JPanel. Я хочу, чтобы определенное действие выполнялось, когда я нажимаю кнопку «w». Я следую учебнику Java по созданию привязок, но метод actionPerformed не выполняется (т. Е. Текст не распечатывается). Ниже полнота коды для моего тестового GUI, с соответствующей частью Мелированной:Java Key Bindings Not Working

import java.awt.BorderLayout; 
import java.awt.event.ActionEvent; 

import javax.swing.AbstractAction; 
import javax.swing.JFrame; 
import javax.swing.JPanel; 
import javax.swing.KeyStroke; 

@SuppressWarnings("serial") 
public class Test extends JFrame{ 

private JPanel panel; 

public Test(){ 
    super(); 
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
    setSize(500,500); 
    setLayout(new BorderLayout()); 
    setVisible(true);   
    panel = new JPanel(); 

    // HERE ARE THE KEY BINDINGS 
    panel.getInputMap().put(KeyStroke.getKeyStroke('w'),"forward"); 
    panel.getActionMap().put("forward", new AbstractAction(){ 
     @Override 
     public void actionPerformed(ActionEvent e){ 
      System.out.println("test"); 
     } 
    }); 
    // END OF KEY BINDINGS 

    add(panel, BorderLayout.CENTER); 
} 

public static void main(String[] args){ 
    new Test();  
} 

} 

текста «тест» никогда не печатаются. Я пробовал много раз со многими различными вариантами, разными ключами, и я уверен, что панель находится в фокусе, но не повезло. Что я делаю не так?

ответ

13

Проблема заключается в том, как вы смотрите KeyStroke. KeyStroke.getKeyStroke('w') вернет typed w, который по какой-то причине не вызывает ключевое событие. Вот почему я стараюсь избегать этого метода. Вместо того, чтобы использовать

panel.getInputMap().put(KeyStroke.getKeyStroke("W"),"forward"); 

или

panel.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_W, 0),"forward"); 

Кроме того, вы можете определить фокус ограничение для InputMap, что-то вроде

panel.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW)... 

Было бы безопаснее ... но вам нужно будет чтобы определить, на каком уровне вы хотите, чтобы нажатия клавиш были активированы от

См. JComponent и How to use Key Bindings для более подробной информации

Обновленные с примером

import java.awt.BorderLayout; 
import java.awt.EventQueue; 
import java.awt.event.ActionEvent; 
import java.awt.event.KeyEvent; 
import javax.swing.AbstractAction; 
import javax.swing.JComponent; 
import javax.swing.JFrame; 
import javax.swing.JPanel; 
import javax.swing.KeyStroke; 
import javax.swing.UIManager; 
import javax.swing.UnsupportedLookAndFeelException; 

public class Test extends JFrame { 

    private JPanel panel; 

    public Test() { 
     super(); 
     setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     setSize(500, 500); 
     setLayout(new BorderLayout()); 
     setVisible(true); 
     panel = new JPanel(); 

     // HERE ARE THE KEY BINDINGS 
     panel.getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW).put(KeyStroke.getKeyStroke(KeyEvent.VK_W, 0), "forward"); 
     panel.getActionMap().put("forward", new AbstractAction() { 
      @Override 
      public void actionPerformed(ActionEvent e) { 
       System.out.println("test"); 
      } 
     }); 
     // END OF KEY BINDINGS 

     add(panel, BorderLayout.CENTER); 
    } 

    public static void main(String[] args) { 
     EventQueue.invokeLater(new Runnable() { 
      @Override 
      public void run() { 
       try { 
        UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName()); 
       } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) { 
       } 

       new Test(); 
      } 
     }); 
    } 
} 
+0

Не заметил, что вы использовали ' 'w'', думал, что вы используете' "ш" '. Обновлено рабочим примером – MadProgrammer