gpt4 book ai didi

c++ - 为基于对话框的应用程序实现回调函数

转载 作者:行者123 更新时间:2023-11-28 06:13:45 25 4
gpt4 key购买 nike

我正在阅读一篇关于如何在 Visual C++ 中创建基于对话框的 GUI 应用程序的非常古老的教程(source - 葡萄牙语)。基于我对 WinAPI 编程的薄弱了解,我决定修改建议的代码主要是为了实现两件事:

1) 与Unicode编程标准的一致性(使用wWinMainMessageBoxW代替WinMain MessageBox/MessageBoxA 例如)。这样的“标准”似乎是到处强制执行的。示例:this question (comments)

2) 创建非空 Win32 项目 时与 Visual Studio 呈现的模型一致。我这样做并注意到:

  • “关于”对话框的回调函数类型为INT_PTR,而不是BOOL
  • WndProc 函数返回 0,而不是教程中的 TRUE(即 1);
  • msg 变量的 switch 语句默认返回 DefWindowProc() 而不是 FALSE;
  • 未指定 WM_CLOSE 处理(我猜对话框对某些事件有默认处理)。

_
结果,出现了一个奇怪的行为,其中名为 Confirm 的 MessageBox 失去了焦点 - 即我无法单击 OK 和 Cancel 按钮。

问题:我的假设是否正确,即 Visual Studio 生成的模板代码比教程中的代码更正确,这对我来说似乎不可信?如果是,我忘记了什么吗?我的代码有什么问题,为什么我不能点击 Messagebox 按钮?

我的最终代码如下:

#define WIN32_LEAN_AND_MEAN
#include <Windows.h>
#include "resource.h"

INT_PTR CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch (msg)
{
case WM_INITDIALOG:
return (INT_PTR)TRUE;
case WM_DESTROY:
PostQuitMessage(0);
break;
case WM_COMMAND:
switch (LOWORD(wParam))
{
case IDOK:
if (MessageBoxW(hWnd, L"Close?", L"Confirm", MB_OKCANCEL) == IDOK)
DestroyWindow(hWnd);
break;
// more code to place here
}
break;
default:
return DefWindowProc(hWnd, msg, wParam, lParam);
}
return 0;
}

int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow)
{
int ret = DialogBoxW(hInstance, MAKEINTRESOURCEW(IDD_DIALOG1), NULL, WndProc);

return 0;
}

为了完整起见,下面是基于教程的代码,实际上工作正常:

BOOL CALLBACK WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch (msg)
{
case WM_INITDIALOG:
return TRUE;
case WM_CLOSE:
DestroyWindow(hWnd);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
case WM_COMMAND:
switch (LOWORD(wParam))
{
case IDOK:
if (MessageBoxW(hWnd, L"Close?", L"Confirm", MB_OKCANCEL) == IDOK)
DestroyWindow(hWnd);
break;
}
break;
default:
return FALSE;
}

return TRUE;
}

最佳答案

所以,我明白了。 Visual Studio 向导创建的代码确实演示了 Windows API 的正确实现。

注意事项:

  • 对话框程序不应调用 DefWindowProc()。这就是 MessageBox 无法正常工作的原因,正如 Hans Passant 在评论中指出的那样。

  • 顾名思义,VS 生成的WndProc() 函数的目的是为主应用程序窗口处理消息。还有另一个函数 About(),它处理“关于”对话框的消息。

  • 对话框过程的返回类型是 INT_PTR,这是对 BOOL 的改进,因为它通过具有64 位环境中的不同大小,避免了可移植性问题。

  • switch block 不需要 default 子句:

Unlike a window procedure, a dialog box procedure never calls theDefWindowProc function. Instead, it returns TRUE if it processes amessage or FALSE if it does not.
(Dialog Box Programming Considerations - MSDN)

  • 对话框默认处理事件:

The (DialogBox) function (...) starts its own message loop to retrieveand dispatch messages for the dialog box.
(DialogBox function - MSDN)

不需要像我那样处理WM_DESTROY - 甚至WM_DESTROY。其实这样做可能会出问题as seen here .

关于c++ - 为基于对话框的应用程序实现回调函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30720956/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com