我有以下代码,旨在将键绑定(bind)映射添加到 JFrame。不幸的是,虽然它可以编译并且在运行程序时没有出现错误,但绑定(bind)不起作用。
我错过了什么?
(defn create-action
"Returns an Action that, when called, executes the given fn."
[f]
(proxy [AbstractAction] []
(actionPerformed [e] (f))))
(defn init-jframe-key-bindings!
"Adds the keybindings to the frame.
keymap take the form of:
{\"KEYSTROKE\" [:key-name fn]
...}"
[frame keymap]
(let [actionmap (.getActionMap (.getRootPane frame))
inputmap (.getInputMap (.getRootPane frame) JComponent/WHEN_ANCESTOR_OF_FOCUSED_COMPONENT)]
(doseq [[keystroke [keyword action]] keymap]
(.put actionmap (name keyword) (create-action action))
(.put inputmap (KeyStroke/getKeyStroke keystroke) (name keyword)))))
绑定(bind)的添加方式如下:
(doto frame
(.setFocusable true)
(init-jframe-key-bindings!
{"RIGHT" [:next-view to-next-view]
"LEFT" [:prev-view to-previous-view]
"T" [:thresh-test conduct-thresh-test]
"A" [:add-marks #(dosync (ref-set ref-mark-mode :a))]
"D" [:del-marks #(dosync (ref-set ref-mark-mode :d))]}))
编辑解决方案是使用JComponent/WHEN_IN_FOCUSED_WINDOW
代替JComponent/WHEN_ANCESTOR_OF_FOCUSED_COMPONENT
。我不确定为什么会出现这种情况,因为焦点应该满足成为焦点组件祖先的要求(但也许不是,因为我有无数的组件)并且仍然很想听到答案,但是有为后代提供解决方案。
最佳答案
for
是懒惰的。您的 init-jframe-key-bindings!
函数正在被调用,它返回一个惰性序列,当实现该序列时,实际上会添加键绑定(bind)。但你从未意识到它;你扔掉它的结果。如果您想要副作用,请使用 doseq
而不是 for
。
关于java - 在框架上启动键绑定(bind),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8423034/