SetWindowRgn 函数是 Win32 API 中的一个函数,用于设置窗口的剪辑区域。通过设置剪辑区域,可以将窗口的形状限制为矩形以外的任何形状。

以下是一个使用 C# 调用 SetWindowRgn 函数的示例代码:

[DllImport("user32.dll", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool SetWindowRgn(IntPtr hWnd, IntPtr hRgn, bool bRedraw);

[DllImport("gdi32.dll")]
static extern IntPtr CreateRoundRectRgn(int nLeftRect, int nTopRect, int nRightRect, int nBottomRect, int nWidthEllipse, int nHeightEllipse);

private void SetWindowShape(IntPtr hWnd, int radius)
{
    // 计算窗口客户区域的大小
    var rect = new RECT();
    GetClientRect(hWnd, out rect);

    // 计算窗口的边框大小
    var style = GetWindowLong(hWnd, GWL_STYLE);
    var exStyle = GetWindowLong(hWnd, GWL_EXSTYLE);
    AdjustWindowRectEx(ref rect, style, false, exStyle);

    // 计算窗口的位置和大小
    var x = rect.Left;
    var y = rect.Top;
    var width = rect.Right - rect.Left;
    var height = rect.Bottom - rect.Top;

    // 创建圆角矩形区域
    var region = CreateRoundRectRgn(0, 0, width, height, radius, radius);

    // 设置窗口的剪辑区域
    SetWindowRgn(hWnd, region, true);
}

该代码中,SetWindowShape() 函数接受一个 hWnd 参数,表示要设置形状的窗口的句柄,以及一个 radius 参数,表示圆角的半径。该函数首先使用 GetClientRect() 函数获取窗口客户区域的大小,然后使用 GetWindowLong() 函数获取窗口的样式和扩展样式,并使用 AdjustWindowRectEx() 函数计算窗口的位置和大小。接着,使用 CreateRoundRectRgn() 函数创建一个圆角矩形区域,并使用 SetWindowRgn() 函数将该区域设置为窗口的剪辑区域,实现了将窗口形状设置为圆角矩形的效果。

需要注意的是,SetWindowRgn 函数只对非标准窗口样式(如 WS_POPUPWS_EX_LAYERED)的窗口生效。对于标准窗口样式的窗口,需要在窗口的 WM_PAINT 消息处理函数中进行自绘来实现窗口的非矩形形状。此外,使用 SetWindowRgn 函数设置窗口的剪辑区域可能会影响窗口的行为和性能,应谨慎使用。