Java Robot类模拟人类鼠标移动

Sha*_*ien 9 java mouse awt

我正在开发一个关于远程控制的项目,从客户端向服务器发送conrdinate x和y游标.

robot.mouseMove(x,y);
Run Code Online (Sandbox Code Playgroud)

只会将光标移动到特定点而不将光标移动到原点

我发现这个简单的algorthim可以模拟鼠标的持续运动

for (int i=0; i<100; i++){
   int x = ((end_x * i)/100) + (start_x*(100-i)/100);
 int y = ((end_y * i)/100) + (start_y*(100-i)/100);
 robot.mouseMove(x,y);
} 
Run Code Online (Sandbox Code Playgroud)

但是这个algorthim仍然太简单了,它只是缓慢地从一个点移动到另一个点,这仍然不像人类的行为.

我从网上读过一些关于远程控制的开放式代码,我发现这个项目 http://code.google.com/p/java-remote-control/ 正在使用来自MouseListener类的方法调用MosueMovement,他们使用这个方法执行"拖动".

我想知道是否有人知道更好的方法吗?

Joe*_*oey 10

如果你想让人造运动变得自然,有几点需要考虑,我想:

  1. 由于鼠标指针在手腕周围枢转,因此人体鼠标移动通常处于轻微弧度.此外,水平运动的弧度比垂直运动更明显.
  2. 人类倾向于向大方向发展,经常超过目标,然后回到实际目标.
  3. 朝向目标的初始速度非常快(因此上述过冲),然后对于精确定位而言稍慢.但是,如果光标最初接近目标,则不会发生快速移动(并且也不会发生过冲).

但是,在算法中制定这一点有点复杂.


Joo*_*ali 7

对于未来的任何人:我开发了一个 Java 库,它模仿人类鼠标的移动。运动中的噪声/锯齿、正弦弧、稍微超出位置等。此外,该库在编写时考虑了扩展和配置的可能性,因此如果默认解决方案与情况不匹配,任何人都可以对其进行微调。现已可从 Maven Central 获取。

https://github.com/JoonasVali/NaturalMouseMotion


dav*_*tto 5

看看我写的这个例子。您可以改进它以模拟乔伊所说的话。我写得非常快,还有很多可以改进的地方(算法和类设计)。请注意,我只处理从左到右的运动。

import java.awt.AWTException;
import java.awt.MouseInfo;
import java.awt.Point;
import java.awt.Robot;

public class MouseMoving {

    public static void main(String[] args) {
        new MouseMoving().execute();
    }

    public void execute() {
        new Thread( new MouseMoveThread( 100, 50, 50, 10 ) ).start();
    }

    private class MouseMoveThread implements Runnable {

        private Robot robot;
        private int startX;
        private int startY;
        private int currentX;
        private int currentY;
        private int xAmount;
        private int yAmount;
        private int xAmountPerIteration;
        private int yAmountPerIteration;
        private int numberOfIterations;
        private long timeToSleep;

        public MouseMoveThread( int xAmount, int yAmount,
                int numberOfIterations, long timeToSleep ) {

            this.xAmount = xAmount;
            this.yAmount = yAmount;
            this.numberOfIterations = numberOfIterations;
            this.timeToSleep = timeToSleep;

            try {

                robot = new Robot();

                Point startLocation = MouseInfo.getPointerInfo().getLocation();
                startX = startLocation.x;
                startY = startLocation.y;

            } catch ( AWTException exc ) {
                exc.printStackTrace();
            }

        }

        @Override
        public void run() {

            currentX = startX;
            currentY = startY;

            xAmountPerIteration = xAmount / numberOfIterations;
            yAmountPerIteration = yAmount / numberOfIterations;

            while ( currentX < startX + xAmount &&
                    currentY < startY + yAmount ) {

                currentX += xAmountPerIteration;
                currentY += yAmountPerIteration;

                robot.mouseMove( currentX, currentY );

                try {
                    Thread.sleep( timeToSleep );
                } catch ( InterruptedException exc ) {
                    exc.printStackTrace();
                }

            }

        }

    }

}
Run Code Online (Sandbox Code Playgroud)