c# - 如何让我的 C# PictureBox 传播鼠标事件? (提供截图)

标签 c# forms events picturebox

我正在使用 C# 窗体创建一个程序,它充当另一个应用程序窗口顶部的覆盖层。整个窗体几乎是一个透明的 PictureBox,它横跨整个区域并在这里和那里绘制形状。

现在我只能和覆盖完全透明的底层窗口交互,如何让非透明区域不拦截鼠标事件?

为清楚起见,这里有一个屏幕截图:
enter image description here

Skype 是底层应用程序。我的叠加层绘制了蓝色(和灰色)框。我需要能够点击框下方的链接。

不幸的是,我没有代码可以展示,因为我不确定程序的哪一部分实际处理这样的事情。

谢谢。

最佳答案

您可以尝试订阅形状点击事件,然后通过某些 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);
}

关于c# - 如何让我的 C# PictureBox 传播鼠标事件? (提供截图),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13399689/

相关文章:

java - 填充 Struts 2 选择菜单并重定向操作

php - Zf2 如何使用过滤器类传递参数?

wpf - 有没有办法处理 pin/unpin 事件 devexpress LayoutPanel

c# - 使用查询字符串 MVC 将数组传递给 View

c# - 映射到程序的虚拟驱动器

c# - 是什么让 Winform 职位最初变得陈旧?

jquery - 将li的内容包裹在标签中

events - 兄弟组件之间的 Angular 2 事件捕获

javascript - 覆盖之前绑定(bind)的点击事件

c# - 跨平台服务(通过c#客户端连接java服务)