4

私は、Teamviewer を楽しみのためのソフトウェアのようにしようとしています。これにより、ある人が別の人の画面を表示したり、クリックしたりできるようになります。とにかく、私はほとんどすべてのソケット関連の作業を完了しましたが、マウス クリックを正しく機能させる方法がわかりません。プログラムでマウスを動かすためにオンラインで見つけたコードは次のとおりです。

  public static class VirtualMouse
{
    // import the necessary API function so .NET can
    // marshall parameters appropriately
    [DllImport("user32.dll")]
    static extern void mouse_event(int dwFlags, int dx, int dy, int dwData, int dwExtraInfo);

    // constants for the mouse_input() API function
    private const int MOUSEEVENTF_MOVE = 0x0001;
    private const int MOUSEEVENTF_LEFTDOWN = 0x0002;
    private const int MOUSEEVENTF_LEFTUP = 0x0004;
    private const int MOUSEEVENTF_RIGHTDOWN = 0x0008;
    private const int MOUSEEVENTF_RIGHTUP = 0x0010;
    private const int MOUSEEVENTF_MIDDLEDOWN = 0x0020;
    private const int MOUSEEVENTF_MIDDLEUP = 0x0040;
    private const int MOUSEEVENTF_ABSOLUTE = 0x8000;


    // simulates movement of the mouse.  parameters specify changes
    // in relative position.  positive values indicate movement
    // right or down
    public static void Move(int xDelta, int yDelta)
    {
        mouse_event(MOUSEEVENTF_MOVE, xDelta, yDelta, 0, 0);
    }


    // simulates movement of the mouse.  parameters specify an
    // absolute location, with the top left corner being the
    // origin
    public static void MoveTo(int x, int y)
    {
        mouse_event(MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE, x, y, 0, 0);
    }


    // simulates a click-and-release action of the left mouse
    // button at its current position
    public static void LeftClick()
    {
        mouse_event(MOUSEEVENTF_LEFTDOWN, Control.MousePosition.X, Control.MousePosition.Y, 0, 0);
        mouse_event(MOUSEEVENTF_LEFTUP, Control.MousePosition.X, Control.MousePosition.Y, 0, 0);
    }
}

ここで、MoveTo メソッドを使用してマウスを移動したいと考えていますが、移動には非常に大きな数値が必要です。とにかく、ここに移動するための座標を画面上の位置にピクセル単位で一致させることができますか? これが明白な質問のように思われる場合は申し訳ありませんが、ほぼ 1 時間グーグルで検索しましたが、マウスの x と y の位置に使用されている単位についての議論が見つかりません。 1 つのパネルでのクリックとユーザーの画面でのクリックを一致させる式。

4

1 に答える 1

6

Microsoftのドキュメントから:

MOUSEEVENTF_ABSOLUTE 値が指定されている場合、dx と dy には 0 ~ 65,535 の正規化された絶対座標が含まれます。イベント プロシージャは、これらの座標を表示面にマップします。座標 (0,0) は表示面の左上隅にマップされ、(65535,65535) は右下隅にマップされます。

これを使用して、次のように、入力をピクセル単位で目的の値に変換できます。

var inputXinPixels = 200;
var inputYinPixels = 200;
var screenBounds = System.Windows.Forms.Screen.PrimaryScreen.Bounds;
var outputX = inputXinPixels * 65535 / screenBounds.Width;
var outputY = inputYinPixels * 65535 / screenBounds.Height;
MoveTo(outputX, outputY);

これは、複数のモニターでは正しくない場合があることに注意してください。また、ドキュメントには次のように記載されていることに注意してください。

この関数は置き換えられました。代わりにSendInputを使用してください。

補遺: J3soon が指摘したように、上記の式は最適ではない可能性があります。AutoHokey の内部で行われた調査に基づいて、次のコードがより適切に機能します。

var outputX = (inputXinPixels * 65536 / screenBounds.Width) + 1;
var outputY = (inputYinPixels * 65536 / screenBounds.Height) + 1;

参照用にAutoHotkey のソース コードを参照してください。


私があなたの立場なら、Cursor.Position を使用します。次のコードは期待どおりに機能します。

System.Windows.Forms.Cursor.Position = new System.Drawing.Point(200, 200);

はい、マウス ポインターを画面の座標 (200、200) ピクセルに配置します [LinqPad でテスト済み]。

補遺System.Windows.Forms.Cursor.Position:少なくとも Windows 上の Mono では、内部で使用されているものを見てきました。への呼び出しSetCursorPosです。奇妙な座標変換は必要ありません。

于 2012-10-13T06:32:38.740 に答える