如何制作带有玻璃背景的窗户

How to make a window with a glass background?

本文关键字:背景 窗户 玻璃 何制 作带      更新时间:2023-10-16

我正在尝试制作一个带有玻璃背景的窗口,但它不起作用。查看我的代码:

LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) {
    switch (message) {
        case WM_ERASEBKGND: {
            RECT rect;
            GetClientRect(hWnd, &rect);
            FillRect(GetDC(hWnd), &rect, (HBRUSH)GetStockObject(BLACK_BRUSH));
            return(0);
        } case WM_PAINT: {
            RECT rect;
            GetClientRect(hWnd, &rect);
            rect.bottom = 262;
            FillRect(GetDC(hWnd), &rect, (HBRUSH)COLOR_WINDOW);
            return(0);
        } case WM_CREATE: {
            if (IsWindowsVistaOrGreater()) {
                BOOL IsCompositionEnabled = FALSE;
                DwmIsCompositionEnabled(&IsCompositionEnabled);
                if (IsCompositionEnabled) {
                    MARGINS margins = {0, 0, 0, 0};
                    margins.cyBottomHeight = 100;
                    HRESULT hr = DwmExtendFrameIntoClientArea(hWnd, &margins);
                    if (SUCCEEDED(hr)) {
                    }
                }
            }
            return(0);
        } case WM_CLOSE: {
            DestroyWindow(hWnd);
            return(0);
        } case WM_DESTROY: {
            PostQuitMessage(0);
            return(0);
        } default: {
            return(DefWindowProc(hWnd, message, wParam, lParam));
        }
    }
}

此代码创建以下窗口:查看图像

这个窗口是我正在尝试做的,但有一个问题。当我移动窗口时,它会闪烁。为什么会闪烁?

您应该更改一些内容:

当你处理WM_PAINT时,你应该打电话给BeginPaint来获取你的绘画的DC和其他信息,然后在完成后打电话给EndPaint。这为您提供了一个 DC,将您的绘画限制在所需的剪切区域,并防止闪烁。

case WM_PAINT: {
    PAINTSTRUCT ps;
    HDC hdc = BeginPaint(hWnd, &ps);
    RECT rect;
    GetClientRect(hWnd, &rect);
    rect.bottom = 262;
    FillRect(hdc, &rect, (HBRUSH)COLOR_WINDOW);
    EndPaint(hWnd, &ps);
    return(0);
}

您还应该在完成擦除后从WM_ERASEBKGND返回 1。

擦除时要使用的HDC传入wParam因此请使用该而不是窗口 DC。

case WM_ERASEBKGND: {
    RECT rect;
    GetClientRect(hWnd, &rect);
    FillRect((HDC)(wParam), &rect, (HBRUSH)GetStockObject(BLACK_BRUSH));
    return(1);
}