如何检查大写锁定键是否已按下?

8

好的,在这被标记为可能重复之前,我已经尝试了以下代码:

Toolkit.getDefaultToolkit().getLockingKeyState(KeyEvent.VK_CAPS_LOCK)

而且对于我来说它总是返回false [如下所示]。有人能否确认这是否应该正常工作,我是在误用它,还是已知它已经损坏?如果它确实损坏了,是否有更好的方法可用?
编辑:好吧,刚发现了更多的东西。它似乎只是返回程序启动时的状态。如果我将该程序开启,则它会显示为开启状态,反之亦然。这是我的代码:
while (true) {
    boolean isOn = Toolkit.getDefaultToolkit().getLockingKeyState(
        KeyEvent.VK_CAPS_LOCK);
    System.out.println("Caps lock is now: " + (isOn ? "ON" : "off"));
    try {
        Thread.sleep(1000);
    } catch (InterruptedException e) {
    }
}

这只是一直打印出它最初的内容

例如,如果我刚开始时大写锁定是开启的,即使我立即切换它,它也会打印:

大写锁定现在为:开启

大写锁定现在为:开启

大写锁定现在为:开启

大写锁定现在为:开启

等等,如果我开始时关闭它,无论如何它都不会打印开启。


2
什么能够或不能够工作将取决于您的环境。什么是环境?图形用户界面环境与命令行环境完全不同。 - Hot Licks
1
@Hot Licks 不确定你的意思是什么,但请看我的编辑 - Alex Coleman
1
这个和编程有关吗?http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4414164 - Senthil Kumar
1
@HotLicks 嗯。你被扣了一分是因为你很蠢吗?我的意思是我不确定你的意思,也就是请进一步解释。你不能因为别人问你某事的意思而对他们进行负面评价。 - Alex Coleman
1
@HotLicks 我是在Windows上使用Eclipse运行的,但我不希望操作系统对其产生影响(也就是说,如果你有一个针对Windows的解决方案,我希望它能在任何操作系统上都能工作)。 - Alex Coleman
显示剩余6条评论
3个回答

5
我认为getLockingKeyState()可能有问题。

你可以尝试使用KeyboardUtils,但这意味着你必须承担JNA的开销。


我想最终会使用JNI并添加全局键监听器;因为我可以在启动时获取大写锁定状态,并检测其何时更改(当按下按钮时),所以我应该能够只需在布尔值中跟踪它并在需要时切换。 - Alex Coleman
1
@Dave,您可以举个KeyboardUtils使用的例子吗? - Alexej Magura
@AlexejMagura:抱歉,不行。这是我知道的东西,但从未使用过。 - Dave

1

看起来这个问题一直存在,或者至少从Java 1.3开始就存在(参见Bug 4414164)。

对于其他平台不确定,但是对于Windows,我可以说:大写锁定键的状态变化可以被检测到,但前提是您的awt客户端有焦点。然而,这个解决方法对我有效:

boolean isCapsLockOn() {
    java.awt.Robot robot = new java.awt.Robot();
    robot.keyPress(KeyEvent.VK_CONTROL);
    robot.keyRelease(KeyEvent.VK_CONTROL);
    return Toolkit.getDefaultToolkit().getLockingKeyState(KeyEvent.VK_CAPS_LOCK);  
}

约束条件:在调用isCapsLockOn之前,您的awt应用程序必须具有焦点。

注意:您的机器人可能会按下任何对您的应用程序无害的其他键。可能取决于您的用例。


-1
public void checkOnOff() {
    Thread th = new Thread() {
        public void run() {
            for (;;) {
                if (Toolkit.getDefaultToolkit().getLockingKeyState(KeyEvent.VK_CAPS_LOCK)) {
                    jLabel4.setForeground(Color.red);
                    jLabel4.setText("CAPSLOCK is ON");
                } else {
                    jLabel4.setText(null);
                }
                try {
                    sleep(100);
                } catch (InterruptedException ex) {
                    Logger.getLogger(Login.class.getName()).log(Level.SEVERE, null, ex);
                }                    
            }
        }
    };th.start();
}

你可以用System.out.println()替换jLabel4.setText(YOURTEXT)。 - Joseph Wanjohi
请解释您的解决方案,不要只写代码。 - Utkarsh

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接