簡體   English   中英

Windows C ++-在類中創建窗口使它看起來異常

[英]Windows C++ - Creating window in a class makes it look unusual

好的,所以我做了一個創建HWND的類。

但是,創建的窗口顯示了一些奇怪的屬性:它與其他窗口不同-它是不透明的,close-minimize-maximize按鈕的位置與普通窗口不同。

但是指定的樣式是默認樣式(WM_OVERLAPPEDWINDOW)。

而且,除非我稍稍移動一下,否則它就無法關閉(好像它在移動前未生成WM_DESTROY或WM_CLOSE消息)。

這可能與WinProc主程序使用指針調用另一個消息處理程序的實現有關。 但是,我不知道為什么窗戶看起來異常。

我的代碼:

//mywind.h
class Window
{
private:
    HWND mHwnd;
    const char* className="Window";
    static LRESULT CALLBACK StartWindowProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam); //main WindowProc function
    LRESULT ThisWindowProc(UINT msg, WPARAM wParam, LPARAM lParam); //Another, object-specific message processing function
    bool isClassRegistered(HINSTANCE hinst);

public:
    Window() : mHwnd( 0 ) { }
    ~Window();

    int create(std::string title, int width, int height);
};

//mywind.cpp
Window::~Window()
{
    if( mHwnd ) DestroyWindow( mHwnd );
}

int Window::create(std::string title, int width, int height)
{
    WNDCLASS wincl;
    HINSTANCE hInst = NULL;
    hInst = GetModuleHandle(NULL);

    if(hInst==NULL)
    {
        printf("Failed to load hInstance\n");
        return -1;
    }

    if(!GetClassInfo(hInst, className, &wincl))
    {
        printf("Getting class info.\n");

        wincl.style = 0;
        wincl.hInstance = hInst;
        wincl.lpszClassName = className;
        wincl.lpfnWndProc = StartWindowProc;
        wincl.cbClsExtra = 0;
        wincl.cbWndExtra = 0;
        wincl.hIcon = NULL;
        wincl.hCursor = NULL;
        wincl.hbrBackground = (HBRUSH)(COLOR_BTNFACE+1);
        wincl.lpszMenuName = NULL;

        if(!isClassRegistered(hInst))
        {
            if (RegisterClass(&wincl) == 0)
            {
                printf("The class failed to register.\n");
                return 0;
            }
        }
    }

    mHwnd = CreateWindow(className, title.c_str(), WS_VISIBLE | WS_OVERLAPPEDWINDOW,
                     CW_USEDEFAULT, CW_USEDEFAULT, width, height,
                     NULL, NULL, hInst, this);
    if(mHwnd==NULL)
    {
        printf("Failed to create HWND.\n");
        return -1;
    }

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

    printf("Destroying window.\n");

    if(mHwnd) DestroyWindow(mHwnd);
    mHwnd=NULL;

    printf("Returning.\n");

    return msg.wParam;
}

bool Window::isClassRegistered(HINSTANCE hinst)
{
    WNDCLASSEX clinf;
    if(!GetClassInfoEx(hinst, className, &clinf)) return false;
    return true;
}

LRESULT CALLBACK Window::StartWindowProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
    Window* winp = NULL;

    if(msg == WM_CREATE)
    {
        CREATESTRUCT* cs = (CREATESTRUCT*) lParam;
        winp = (Window*) cs->lpCreateParams;

        SetLastError(0);
        if(SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR) winp) == 0)
        {
            if(GetLastError()!=0) return -1;
        }
    }
    else
    {
        winp = (Window*) GetWindowLongPtr(hwnd, GWLP_USERDATA);
    }

    if(winp) return winp->ThisWindowProc(msg, wParam, lParam);

    return DefWindowProc(hwnd, msg, wParam, lParam);
}

LRESULT Window::ThisWindowProc(UINT msg, WPARAM wParam, LPARAM lParam)
{
    switch(msg)
    {
    case WM_PAINT:
        return 0;

    case WM_DESTROY:
        PostQuitMessage(0);
        return 0;

    case WM_CLOSE:
        PostQuitMessage(0);
        return 0;

    default:
        return DefWindowProc(mHwnd, msg, wParam, lParam);
    }

    return 0;
}

//main.cpp

#include "mywind.h"

int main(int argc, char* argv[])
{
    Window mwnd;
    mwnd.create("Test", 200, 200);

    return 0;
}

請注意,直到CreateWindowEx返回時才設置mHwnd 這意味着在窗口創建期間發送的所有消息都將0傳遞給DefWindowProc而不是實際的窗口句柄。 這使窗口管理器認為您正在繞過默認處理並執行自定義標題,這就是為什么一切看起來不正確的原因。

TL; DR:在WM_NCCREATE處理程序中設置mHwnd

我90%確信您的問題是缺少清單,該清單使WinXP / 7看起來更漂亮。 現在您處於兼容模式,並且窗口框架適用於Windows 98/2000樣式。 有關更多詳細信息,請閱讀此鏈接(或針對同一問題的許多其他鏈接): http : //www.mctainsh.com/Articles/Csharp/XpControlsInCS.aspx

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM