普通窗口没有静态窗口,您应该尝试查找如何使用 RegisterWindowEx 注册和处理您自己的类,然后使用相同的类名创建一个窗口。您必须拥有自己的窗口过程才能处理消息。系统注册的所有窗口类都运行自己的默认窗口程序,据我所知,它们都没有处理 WM_CLOSE (即关闭按钮),这就是您无法关闭它的原因。
对你来说,主窗口总是使用类似 WS_OVERLAPPEDWINDOW 的东西,这样就可以清楚地知道它是否可以,并从中消除你不需要的标志。
你如何设置它:
WNDCLASSEX wndcls;
HWND hMainWnd;
// Register your own window class
ZeroMemory(&wndcls,sizeof(WNDCLASSEX));
wndcls.cbSize=sizeof(WNDCLASSEX);
wndcls.style=CS_VREDRAW+CS_HREDRAW;
wndcls.lpfnWndProc=&appWndFunc;
wndcls.hInstance=hInstance;
wndcls.hIcon=hMainIcon; // or just LoadIcon(hInstance,MAKEINTRESOURCE(IDI_MAIN_ICON))
wndcls.hIconSm=hMainIcon;
wndcls.hCursor=LoadCursor((HINSTANCE)NULL,IDC_ARROW);
wndcls.hbrBackground=(HBRUSH)COLOR_APPWORKSPACE;
wndcls.lpszClassName="myWndClass";
if (RegisterClassEx(&wndcls)==0)
{
// failed to register class name
return false;
}
// Create window with your own class
hMainWnd=CreateWindowEx(0,\
"myWndClass","widnow title",\
WS_OVERLAPPEDWINDOW|WS_VISIBLE,\
0,\
0,\
250,\
250,\
hMainWnd,NULL,hInstance,NULL);
if (hMainWnd==(HWND)NULL)
{
// failed to create main window
return false;
}
然后你的主循环:
bool bAppMainLoop=false
while(!bAppMainLoop)
{
WaitMessage();
while(PeekMessage(&emsg,NULL,0,0,PM_NOREMOVE))
{
if(GetMessage(&emsg,NULL,0,0)==0)
{
bAppMainLoop=true;
break;
}
TranslateMessage(&emsg);
DispatchMessage(&emsg);
}
}
这比通常的设置要多一些,所以让我解释一下,为了不烧毁 CPU,你等待带有 WaitMessage 的消息,它会阻塞直到发生某些事情,比如移动窗口、单击、绘画等。PeekMessage 将返回 true如果有消息,那么在 while 循环中调用它会确保它耗尽消息队列,如果 GetMessage 返回 0,它将获取消息,这意味着您的应用程序调用了 PostQuitMessage(0),因此在消息中找到了 WM_QUIT循环,这意味着是时候脱离消息循环了。其余的 Translate and Dispatch 就如其名。
最后,您需要自己的窗口过程:
LRESULT CALLBACK appWndFunc(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam)
{
if (uMsg==WM_CLOSE)
{
PostQuitMessage(0);
return 0;
}
return DefWindowProc(hWnd,uMsg,wParam,lParam);
}
DefWindowProc 对于处理来自系统的所有常见消息是必不可少的,因此您无需在此处处理这些消息。您只需响应当您想要关闭窗口时发送的 WM_CLOSE 消息并将退出消息发布到您将捕获并退出的消息循环中。
附加信息:不需要释放你的东西,因为 Windows 会为你这样做,所以下次启动程序时它不会被锁定,但至少在你的主循环之后取消注册你的窗口类是一个好习惯。
顺便说一句,这是错误的主要功能:WinMain是正确的。另外,为了避免更多错误,请确保您编译 Windows GUI 应用程序。