我目前正在重新创建snake并使用KeyListener将箭头键绑定到某些命令。最近,我听说Key Bindings更好,并决定进行转换,但几乎不了解Oracle的文章。
现在,要绑定箭头键,我必须这样做:
panel.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT, 0),"left");
panel.getActionMap().put("left", new AbstractAction(){
@Override
public void actionPerformed(ActionEvent e){
addToQueue(LEFT);
}
});
panel.getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_UP, 0),"up");
panel.getActionMap().put("up", new AbstractAction(){
@Override
public void actionPerformed(ActionEvent e){
addToQueue(UP);
}
});
// Another two for right and down are in my code but you get the picture.
必须有一种更简单的方法来做到这一点,对吧?我试着用Google搜索但什么也没找到,我几乎不知道InputMap和ActionMap是什么,所以我不确定从哪里开始。
答案 0 :(得分:1)
好吧,您有一组KeyEvent
,QueueElement
对,可以表示为地图:
ImmutableMap<KeyEvent, QueueElement> KEY_BINDINGS = ImmutableMap.of(
KeyEvent.VK_LEFT, LEFT,
KeyEvent.VK_UP, UP,
...);
然后你可以循环注册这些动作:
for (Entry<KeyEvent, QueueElement> e : KEY_BINDINGS.entrySet()) {
panel.getInputMap().put(KeyStroke.getKeyStroke(e.getKey(), 0),
e.getValue().toString());
panel.getActionMap().put(e.getValue().toString(), new AbstractAction(){
@Override
public void actionPerformed(ActionEvent e){
addToQueue(e.getValue());
}
});
}
这假设您的QueueElement
类型具有有意义的.toString()
,但如果不希望这是一个简单的更改 - 就像您将"up"
之类的字符串与UP
这样的对象相关联一样没有任何意义。最好将其名称作为类型本身的一部分。如果您无法更改.getName()
,则可以提供.toString()
方法或类似方法。
答案 1 :(得分:1)
虽然这只会将问题转储到函数中,但您可以在过程后屏蔽此行为:
void bindKeyToAction(Panel p, KeyEvent ke, String id, Object o){
p.getInputMap().put(KeyStroke.getKeyStroke(ke, 0),id);
p.getActionMap().put(id, new AbstractAction(){
@Override
public void actionPerformed(ActionEvent e){
addToQueue(o);
}
});
}
由于我没有看到你的LEFT和UP对象的对象类型,我在方法中使用了对象o。
所以要绑定,你只需要调用这个函数。
bindKeyToAction(panel, KeyEvent.UP, "up", UP);
bindKeyToAction(panel, KeyEvent.Left, "left", LEFT);