SetWindowRgn 的 Vista 实时缩略图问题

发布于 2024-07-12 23:40:45 字数 2187 浏览 5 评论 0原文

我知道我可能错过了一些东西,但是当使用具有区域的窗口时,我似乎无法让窗口正确显示实时缩略图预览。 当点击最小化按钮时,预览将剪辑为最小化尺寸 (160x25),而不是显示完整预览(就像其他窗口一样)。

有几点需要说明:

1) 预览版在 Windows Live Messenger 中运行良好,因此 Microsoft 找到了一种方法来实现这一点。

2)如果我仅在窗口可见之前调用SetWindowRgn,它就可以正常工作(因此这不是DWM不知道如何处理区域窗口的错误。)我可以在窗口可见之前多次调用SetWindowRgn并且它工作得很好。

3)我需要在显示窗口后设置窗口区域,以防调整大小。 因此,仅在之前设置它的修复方法是行不通的。

4)即使使用默认的窗口过程,该错误仍然发生。 因此,这不是错误处理消息的错误(但可能是“不处理”消息的错误:))

5)通过单击任务栏按钮(而不是窗口中的最小化按钮)最小化时,预览正常工作很好(即使在设置可见区域之后)。 再次证明它并不如何处理预览。

如果我在显示窗口后设置一个区域,则会发生该错误。 遵循的代码:

void create(HINSTANCE hInst)
{
    char* className = "default";

    /* Register
    */
    WNDCLASSEX wcex;
    memset(&wcex,0,sizeof(wcex));
    wcex.cbSize = sizeof(WNDCLASSEX);
    wcex.style          = CS_HREDRAW | CS_VREDRAW;
    wcex.lpfnWndProc    = DefWindowProc;
    wcex.hInstance      = hInst;
    wcex.hCursor        = LoadCursor(NULL, IDC_ARROW);
    wcex.hbrBackground  = (HBRUSH)(COLOR_WINDOW+1);
    wcex.lpszClassName  = className;
    RegisterClassEx(&wcex);

    /* Create
     */
    HWND hwnd = CreateWindow(className, className, WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInst, NULL);

    /* 
     * Set the region
     * If set before the window is shown for the first time, minimize preview on vista works
     */

    RECT rect;
    GetWindowRect(hwnd,&rect);
    HRGN rgn = CreateRoundRectRgn(0,0,rect.right-rect.left,rect.bottom-rect.top,15,15);
    SetWindowRgn(hwnd,rgn,TRUE);

    /* Show the window
     */

    ShowWindow(hwnd,SW_SHOW);

    /* 
     * Set the region a second time.
     * Doing this will break minimize preview on vista
     */

    rgn = CreateRoundRectRgn(0,0,rect.right-rect.left,rect.bottom-rect.top,35,35);
    SetWindowRgn(hwnd,rgn,TRUE);
}

int APIENTRY _tWinMain(HINSTANCE hInstance,
                 HINSTANCE hPrevInstance,
                 LPTSTR    lpCmdLine,
                 int       nCmdShow)
{
    MSG msg;

    create(hInstance);

    while (GetMessage(&msg, NULL, 0, 0))
    {
        TranslateMessage(&msg);
        DispatchMessage(&msg);
    }

    return (int) msg.wParam;
}

I know I am probably missing something, but I can't seem to get windows to show the live thumbnail preview correctly when using a window that has a region. When hitting the minimize button the preview will clip to the minimized size (160x25) rather than showing the full preview (like it does with other windows).

Few points to make:

1) The preview works fine in Windows Live Messenger, so Microsoft figured out a way to do it.

2) If I call SetWindowRgn only before a window is visible, it works fine (so its not a fault of the DWM not knowing how to deal with regioned windows.) I can call SetWindowRgn many times before the window is visible and it works great.

3) I need to set the window region after I show the window in case of a resize. So a fix to just set it before will not work.

4) Even when using the default window procedure, the bug still happens. So it is not a fault of processing a message incorrectly (but could be a fault of 'not processing' one :) )

5) When minimizing by clicking the taskbar button (instead of the minimize button in the window), the preview normally works fine (even after setting the region when visible). Again proving that it does not how to deal with the preview.

The bug happens if I set a region after I have shown the window. Code to follow:

void create(HINSTANCE hInst)
{
    char* className = "default";

    /* Register
    */
    WNDCLASSEX wcex;
    memset(&wcex,0,sizeof(wcex));
    wcex.cbSize = sizeof(WNDCLASSEX);
    wcex.style          = CS_HREDRAW | CS_VREDRAW;
    wcex.lpfnWndProc    = DefWindowProc;
    wcex.hInstance      = hInst;
    wcex.hCursor        = LoadCursor(NULL, IDC_ARROW);
    wcex.hbrBackground  = (HBRUSH)(COLOR_WINDOW+1);
    wcex.lpszClassName  = className;
    RegisterClassEx(&wcex);

    /* Create
     */
    HWND hwnd = CreateWindow(className, className, WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInst, NULL);

    /* 
     * Set the region
     * If set before the window is shown for the first time, minimize preview on vista works
     */

    RECT rect;
    GetWindowRect(hwnd,&rect);
    HRGN rgn = CreateRoundRectRgn(0,0,rect.right-rect.left,rect.bottom-rect.top,15,15);
    SetWindowRgn(hwnd,rgn,TRUE);

    /* Show the window
     */

    ShowWindow(hwnd,SW_SHOW);

    /* 
     * Set the region a second time.
     * Doing this will break minimize preview on vista
     */

    rgn = CreateRoundRectRgn(0,0,rect.right-rect.left,rect.bottom-rect.top,35,35);
    SetWindowRgn(hwnd,rgn,TRUE);
}

int APIENTRY _tWinMain(HINSTANCE hInstance,
                 HINSTANCE hPrevInstance,
                 LPTSTR    lpCmdLine,
                 int       nCmdShow)
{
    MSG msg;

    create(hInstance);

    while (GetMessage(&msg, NULL, 0, 0))
    {
        TranslateMessage(&msg);
        DispatchMessage(&msg);
    }

    return (int) msg.wParam;
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

独孤求败 2024-07-19 23:40:54

微软对技术支持事件做出了回应,并将其列为 Vista 中的一个错误。

Microsoft responded to a tech support incident and listed this as a bug within Vista.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文