2015-07-10 11 views
1

我試圖使程序響應當按鈕ESC被點擊,以便它將處置jframe。我不確定問題是什麼,但它似乎在主菜單中的if語句中。JFrame沒有配置,當我按下轉義

*注:叔是類(文本編輯)對象名稱

這部分是在主方法

f.add(text); 
    f.addKeyListener(te); 
    f.setVisible(true); 

    while(true){ 
     if (exiting == true){ 
      f.dispose(); 
     } 

    } 

該部分是主要的方法

@Override 
public void keyPressed(KeyEvent e) { 
    if (e.getKeyCode() == KeyEvent.VK_ESCAPE){ 
     exiting = true; 

    } 
} 
+0

'我不知道這個問題is'什麼 - 你做任何調試?您是否向KeyListener添加了打印語句以查看代碼是否已執行? – camickr

+0

似乎你在EDT上有一個無限循環,會凍結GUI。 [看看這個](https://docs.oracle.com/javase/tutorial/uiswing/events/keylistener.html) – Titus

+0

我試圖把Thread.sleep(10);在循環內,但它仍然沒有工作 – yj2000

回答

4

不要使用KeyListener s,作爲一般規則,它們所連接的組件必須具有鍵盤焦點才能被觸發。

相反,使用一個密鑰綁定...

InputMap im = getRootPane().getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW); 
ActionMap am = getRootPane().getActionMap(); 

im.put(KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0), "cancel"); 
am.put("cancel", new AbstractAction() { 
    @Override 
    public void actionPerformed(ActionEvent e) { 
     dispose(); 
    } 
}); 

更多細節

因爲Action API的力量見How to Use Key Bindings,我將創建一個基本的「處置」行動開始:

public class DisposeWindowAction extends AbstractAction { 

    private Window window; 

    public DisposeWindowAction(Window window) { 
     this.window = window; 
     putValue(NAME, "Dispose"); 
     putValue(ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_EQUALS, 0)); 
    } 

    public Window getWindow() { 
     return window; 
    } 

    @Override 
    public void actionPerformed(ActionEvent e) { 
     getWindow().dispose(); 
    } 

} 

我然後綁定這個到ActionMap ...

am.put("cancel", new DisposeWindowAction(this)); 

爲什麼你問?因爲你就可以使用在JMenuItem S和JButton s`相同Action ....

JButton disposeButton = new JButton(new DisposeWindowAction(this)); 
... 

(您可以使用Action的同一個實例,但你的想法),現在用戶有類似三個方法來處理窗口...

How to Use Actions更多細節

1

有一個更簡單的方法來將監聽器添加到jframe。你所要做的就是創建一個keylistener來覆蓋keypressed,然後檢查e.getComponent()是什麼類型的對象。如果它是一個窗口類型,您可以在按下退出鍵時調用它。

public void keyPressed(KeyEvent e){ 
    If(e.getKeyCode() == KeyEvent.VK_ESCAPE){ 
     If(e.getComponent() instanceof Window){ 
      ((Window)e.getComponent()).dispose(); 
     } 
    } 
} 

您當然可以將窗口更改爲JFrame,並將兩個if語句放在一起。

你也不需要while循環。

+0

'KeyListener'是一個糟糕的選擇,任何可以抓住鍵盤焦點的組件都會導致你的'KeyListener'被忽略的時刻 – MadProgrammer

+0

@MadProgrammer啊,我不知道關鍵綁定,我有意思的關鍵人員是捕捉關鍵事件的唯一途徑。謝謝你的提示。 –

相關問題