形状のクリック イベントをサブスクライブしてから、いくつかの Windows API を介して「オーバーレイされた」ウィンドウにイベントを転送することができます。アプリケーションのメイン ウィンドウへのポインターがある場合 (Process オブジェクトを介して自分で開始したか、別の方法で取得したかのいずれか)、マウス イベントをそのウィンドウに送信するだけです。
画面の現在のポイントを取得し、それを Skype の最初のインスタンスに送信する例を次に示します。
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = false)]
static extern IntPtr SendMessage(IntPtr hWnd, int Msg, int wParam, int lParam);
[StructLayout(LayoutKind.Explicit)]
struct LParamLocation
{
[FieldOffset(0)]
int Number;
[FieldOffset(0)]
public short X;
[FieldOffset(2)]
public short Y;
public static implicit operator int(LParamLocation p)
{
return p.Number;
}
}
private void Form1_MouseClick(object sender, MouseEventArgs e)
{
var process = Process.GetProcessesByName("skype");
LParamLocation points = new LParamLocation();
points.X = (short)PointToScreen(e.Location).X;
points.Y = (short)PointToScreen(e.Location).Y;
SendMessage(process[0].MainWindowHandle, 0x201, 0, points); //MouseLeft down message
SendMessage(process[0].MainWindowHandle, 0x202, 0, points); //MouseLeft up message
}
または、ウィンドウ スタイルを追加して、すべてのマウス イベントを通過するように指示することもできます。
[DllImport("user32.dll")]
static extern int SetWindowLong(IntPtr hWnd, int nIndex, int dwNewLong);
[DllImport("user32.dll")]
static extern int GetWindowLong(IntPtr hWnd, int nIndex);
protected override void OnHandleCreated(EventArgs e)
{
base.OnHandleCreated(e);
int style = GetWindowLong(Handle, -20);
style |= 0x00000020; // Enables Pass-Through of events
style |= 0x00080000; // Enables Pass-Through to layered windows
SetWindowLong(Handle, -20, style);
}