所以,我有一个奇怪的问题。我正在制作一个可以移动鼠标的 WPF 应用程序。我有以下代码:
[StructLayout(LayoutKind.Sequential)]
private struct POINT
{
public int X;
public int Y;
public static implicit operator Point(POINT point)
{
return new Point(point.X, point.Y);
}
}
[DllImport("user32.dll")]
private static extern bool GetCursorPos(out POINT lpPoint);
[DllImport("user32.dll", EntryPoint = "SetCursorPos")]
private static extern void SetCursorPos(int X, int Y);
private static Random random = new Random(DateTime.Now.Millisecond);
public static Point GetMousePosition()
{
GetCursorPos(out POINT lpPoint);
return lpPoint;
}
public static void MoveMouse(int x, int y, int tolerance = 10)
{
tolerance = Math.Max(0, tolerance);
int startX = GetMousePosition().X;
int startY = GetMousePosition().Y;
int finalX = random.Next(x - tolerance, x + tolerance + 1);
int finalY = random.Next(y - tolerance, y + tolerance + 1);
int diffX = finalX - startX;
int diffY = finalY - startY;
double time = Math.Max(1, Math.Max(Math.Abs(diffX), Math.Abs(diffY)) / (5 + random.NextDouble()));
double deltaX = diffX / time;
double deltaY = diffY / time;
for (int i = 1; i <= time; i++)
{
SetCursorPos((int)(startX + deltaX * i), (int)(startY + deltaY * i));
}
}
长话短说,使用 x,y 坐标调用 MoveMouse(),它将把鼠标移动到屏幕上的该点 ± [容差] 像素。
如果我直接从 Visual Studio 中运行它并附加调试器,一切都会按预期工作。但是,如果在没有调试器的情况下运行,鼠标实际上会移动 2-3 倍慢。我必须加入 Thread.Sleep(1);在 for 循环中只是为了匹配它在发布模式下的功能。
什么给予?我怎样才能让它在“生产”中像在调试中一样快?
澄清一下:“调试”与“发布”配置实际上并没有什么区别。仅当连接调试器时才会有所不同。
如果我没记错的话,当我制作一个在 while(true) 循环中运行某些函数的控制台应用程序时,我观察到类似的问题。因为每个周期之间没有进行睡眠,这意味着该函数会被一次又一次地调用,使应用程序的 CPU 使用率瞬间达到峰值,并持续下去。它使整个系统变慢,因此光标也变得迟缓。
完全没有证据,但我猜因为调试器需要遵循一些事情,它本质上增加了延迟,所以 CPU 使用率会变得很容易。没有接受过有关调试器的教育,因此欢迎对此进行任何解释。
我的解决方法和你的完全一样,只是在中间睡觉。
for (int i = 1; i <= time; i++)
{
SetCursorPos((int)(startX + deltaX * i), (int)(startY + deltaY * i));
Thread.Sleep(100); // 0.1s, might be a little clunky.
}
睡眠时间取决于您的实际需求,但通常电影为 24fps,每次睡眠约 40 毫秒。