首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Awt机器人按键延迟

Awt机器人按键延迟
EN

Stack Overflow用户
提问于 2016-02-13 20:09:36
回答 1查看 2.6K关注 0票数 2

我工作在一个小工具的游戏,类似热键,处理组合的用户按键事件,并模拟与Awt机器人,一对夫妇的按键。问题是,被调用的方法ghostWalk()仅在第一次按下注册组合时才按预期工作,第二次按相同的组合时和调用相同的方法时只调用"robot.delay“之后的最后一个键。请阅读更多代码注释。

代码语言:javascript
复制
import com.melloware.jintellitype.HotkeyListener;
import com.melloware.jintellitype.JIntellitype;
import java.awt.*;
import java.awt.event.InputEvent;
import java.awt.event.KeyEvent;

public class L {
int i = 160;

public static void main(String args[]){
    L l = new L();
    l.k();
}
public void k(){
    // Register keys combination
    JIntellitype.getInstance();
    JIntellitype.getInstance().registerHotKey(1, JIntellitype.MOD_ALT, (int)'D');
    JIntellitype.getInstance().registerHotKey(2, JIntellitype.MOD_ALT, (int)'J');
    JIntellitype.getInstance().registerHotKey(3, JIntellitype.MOD_ALT, (int)'K');
    JIntellitype.getInstance().addHotKeyListener(new HotkeyListener() {
        public void onHotKey(int aIdentifier) {
            // First indentifier Alt + D
            if (aIdentifier == 1) {
                System.out.println("Alt+D hotkey pressed");
                // Start new thread
                new Thread(new Runnable() {
                    @Override
                    public void run() {
                        L gh = new L();
                        gh.ghostWalk();
                    }
                }).start();
            }
            // Second indetifier
            else if(aIdentifier == 2){
                i += 10;
                System.out.println(i);
            }
            // Third
            else if(aIdentifier == 3){
                i -= 10;
                System.out.println(i);
            }
        }
    });
}
// Method called to simulate key press
/* So, first time when i press Alt + D in game after program runs
all work good, the keys are simulated  as expected but if I press again and again
the combination only key "d" are simulated which is after "delay(i), i = 160"
If program is restarted all again is the same, only first time when i press registered
combinations the program work as expected.
Second and others times program work only if there is delay "robot = new Robot();
                                                             robot.delay(100);"
 on 100 delay program work well on 40ms need to press very fast the combination
 so the program work as expected. How to fix it ? to simulate key press without
 delay like first time when program is run.
 P.s no matter in which window(game, notepad) you press combination to simulate key press
 still work good only first time.
Example of output when i press two times combinations in game
first time: qqwewwd
second time: d
 */
public void ghostWalk(){
    Robot robot = null;
    try {
        robot = new Robot();
        //robot.delay(100);
        robot.keyPress(KeyEvent.VK_Q);
        robot.keyRelease(KeyEvent.VK_Q);
        robot.keyPress(KeyEvent.VK_Q);
        robot.keyRelease(KeyEvent.VK_Q);
        robot.keyPress(KeyEvent.VK_W);
        robot.keyRelease(KeyEvent.VK_W);
        robot.keyPress(KeyEvent.VK_R);
        robot.keyRelease(KeyEvent.VK_R);
        robot.keyPress(KeyEvent.VK_W);
        robot.keyRelease(KeyEvent.VK_W);
        robot.keyPress(KeyEvent.VK_W);
        robot.keyRelease(KeyEvent.VK_W);
        robot.delay(i);
        robot.keyPress(KeyEvent.VK_D);
        robot.keyRelease(KeyEvent.VK_D);

    } catch (Exception e) {
        e.printStackTrace();
    }
}

}

编辑:,我不知道在第一次调用ghostWalk方法之后所做的哪些更改,我应该使用延迟,这样我的程序就能像预期的那样工作。

Edit2:当将setAutoWaitForIdle设置为true和delay =5(开始之前的延迟以模拟按键)时,在我的用例代码中的开始工作。如果按键之间是一个延迟,就像我的案例延迟(I)一样,i=160个,那么启动延迟应该是60~。(如果启动延迟为40~那么并不总是工作良好,需要非常快地按下注册密钥组合idk为什么,而且如果启动延迟小于40-60在我的情况下仅模拟最后按键"D“,即延迟(I))。

如果要删除第一次注册的热键事件上的robot.setAutoWaitForIdle(true)robot.delay(60),该工具将按预期工作,在第二次、第三次等时间-不工作。在第一个JIntellitype事件之后,只工作此代码。

代码语言:javascript
复制
public void ghostWalk(){
    Robot robot = null;
    try {
        robot = new Robot();
        robot.setAutoWaitForIdle(true);
        robot.delay(60);
        robot.keyPress(KeyEvent.VK_Q);
        robot.keyRelease(KeyEvent.VK_Q);
        robot.keyPress(KeyEvent.VK_Q);
        robot.keyRelease(KeyEvent.VK_Q);
        robot.keyPress(KeyEvent.VK_W);
        robot.keyRelease(KeyEvent.VK_W);
        robot.keyPress(KeyEvent.VK_R);
        robot.keyRelease(KeyEvent.VK_R);;
        robot.delay(i);
        robot.keyPress(KeyEvent.VK_D);
        robot.keyRelease(KeyEvent.VK_D);

    } catch (Exception e) {
        e.printStackTrace();
    }
}
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2016-02-13 20:44:55

您应该考虑使用setAutoDelay设置一个自动延迟。

很可能你的操作系统在处理输入事件时遇到问题,如果它们被及时发布的话。试着延迟50毫秒或25毫秒,看看会发生什么。

您可以尝试的另一件事是在每个键按下之前添加waitForIdle()

编辑:用于体育--我尝试了JIntelliType库 out,下面的片段工作得比较好。我测试了在Notepad++ (ctrl-Q)中按下热键,它始终打印出tt rocks。但是,我必须快速释放热键,否则Notepad++就开始将热键解释为其他东西(ctrl-Q已经是Notepad++中其他东西的快捷方式)。

使用机器人并不是精确的科学。在让机器人按下键之前,我不得不将机器人延迟150 ms,然后再推迟waitForIdle。否则事情就搞砸了。设置自动延迟是不必要的。

代码语言:javascript
复制
import java.awt.AWTException;
import java.awt.Robot;
import java.awt.event.KeyEvent;
import com.melloware.jintellitype.HotkeyListener;
import com.melloware.jintellitype.JIntellitype;

public class TestKeys {
    private HotkeyListener listener = new HotkeyListener() {
        @Override
        public void onHotKey(final int hotKeyId) {
            new Thread(new Runnable() {
                @Override
                public void run() {
                    JIntellitype.getInstance().removeHotKeyListener(listener);
                    handleHotKey(hotKeyId);
                    JIntellitype.getInstance().addHotKeyListener(listener);
                }
            }).start();
        }
    };

    public void registerHotKeys() {
        JIntellitype instance = JIntellitype.getInstance();
        instance.registerHotKey(1, JIntellitype.MOD_CONTROL, 'Q');
        instance.registerHotKey(2, JIntellitype.MOD_CONTROL, 'J');
        instance.addHotKeyListener(listener);
        System.out.println("Hotkeys registered");
    }

    private static void handleHotKey(int hotKeyId) {
        switch(hotKeyId) {
            case 1:
                System.out.println("Pressing some keys now!");
                pressSomeKeys();
                break;
            case 2:
                System.out.println("Bailing out, cya!");
                System.exit(0);
                break;
        }
    }

    private static void pressSomeKeys() {
        Robot r;
        try {
            r = new Robot();
        } 
        catch (AWTException e) {
            System.out.println("Creating robot failed");
            System.exit(2);
            return;
        }
        r.setAutoWaitForIdle(true);
        r.delay(150);
        r.waitForIdle();
        r.keyPress(KeyEvent.VK_T); r.keyRelease(KeyEvent.VK_T);
        r.keyPress(KeyEvent.VK_T); r.keyRelease(KeyEvent.VK_T);
        r.keyPress(KeyEvent.VK_SPACE); r.keyRelease(KeyEvent.VK_SPACE);
        r.keyPress(KeyEvent.VK_R); r.keyRelease(KeyEvent.VK_R);
        r.keyPress(KeyEvent.VK_O); r.keyRelease(KeyEvent.VK_O);
        r.keyPress(KeyEvent.VK_C); r.keyRelease(KeyEvent.VK_C);
        r.keyPress(KeyEvent.VK_K); r.keyRelease(KeyEvent.VK_K);
        r.keyPress(KeyEvent.VK_S); r.keyRelease(KeyEvent.VK_S);
    }

    public static synchronized void main(String[] args) {
        System.out.println("TestKeys started");
        TestKeys k = new TestKeys();
        k.registerHotKeys();
        try { 
            TestKeys.class.wait();
        } 
        catch (InterruptedException e) {
        }
    }
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35384782

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档