java - 在框架上启动键绑定(bind)

标签 java swing clojure

我有以下代码,旨在将键绑定(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/

相关文章:

java - 错误: Cannot fit requested classes in a single dex file (# methods: 67451 > 65536)

java - 多维 String[][] 数组 java

java - 如何正确对齐 JFrame 内的两个 JPanel

java - 如何绘制自己的工具提示来代替 Swing 组件的默认工具提示?

tomcat - 部署到 Tomcat 的 leinring uberjar 的路由不正确

java - Twitter Storm 的测试 API 不会初始化

java - 生产者消费者修改

java - 用户操作时显示的 Swing 卡布局更改面板

java - 获取面板的 gridbag 约束

clojure - Clojure 中什么时候需要引用列表?