如何创建一个最简单的Windows桌面应用程序 (C++)_c++ 简单的桌面程序

img
img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,涵盖了95%以上C C++开发知识点,真正体系化!

由于文件比较多,这里只是将部分目录截图出来,全套包含大厂面经、学习笔记、源码讲义、实战项目、大纲路线、讲解视频,并且后续会持续更新

如果你需要这些资料,可以戳这里获取

使用ShowWindow函数显示窗口

这部分也很好理解,详见文末的代码

4.侦听消息

添加用于侦听操作系统所发送消息的消息循环。

当应用程序收到一条消息时,此循环将该消息调度到 WndProc 函数。WndProc 函数用于对接收的消息进行处理,我们下面会介绍到。

该消息循环类似于以下代码:

[cpp] 
view plain
 copy

  1. // Main message loop:
  2. // 添加用于侦听操作系统所发送消息的消息循环。
  3. // 当应用程序收到一条消息时,此循环将该消息调度到 WndProc 函数以进行处理。
  4. MSG msg;
  5. while (GetMessage(&msg, NULL, 0, 0)) {
  6. TranslateMessage(&msg); //翻译消息
  7. DispatchMessage(&msg);  //派遣消息
  8. }

WndProc 函数

WndProc 函数用以处理应用程序收到的消息。

首先需要判断收到的消息类型进而做出不同的处理,这需要使用 switch 语句。
     系统提供了众多的消息命令,例如 WM_PAINT 代表收到了绘图消息,而收到鼠标点击消息的标识是WM_LBUTTONDOWN…

这里以处理 WM_PAINT 消息为例进行说明。

要处理 WM_PAINT 消息,首先应调用 BeginPaint,然后处理所有的绘图逻辑,例如在窗口中布局文本、按钮和其他控件,然后调用 EndPaint。

对于此应用程序,开始调用和结束调用之间的逻辑是在窗口中显示字符串 “Hello,World!”。 在以下代码中,TextOut 函数用于显示字符串。

[cpp] 
view plain
 copy

  1. LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) {
  2. PAINTSTRUCT ps;
  3. HDC hdc;
  4. TCHAR greeting[] = _T(“Hello, World!”);
  5. switch (message) {
  6. case WM_PAINT:
  7. //要处理 WM_PAINT 消息,首先应调用 BeginPaint
  8. //然后处理所有的逻辑以及在窗口中布局文本、按钮和其他控件等
  9. //然后调用 EndPaint。
  10. hdc = BeginPaint(hWnd, &ps);
  11. // -----------------在这段代码对应用程序进行布局------------------------
  12. // 对于此应用程序,开始调用和结束调用之间的逻辑是在窗口中显示字符串 “Hello,World!”。
  13. // 请注意 TextOut 函数用于显示字符串。
  14. TextOut(hdc, 50, 5, greeting, _tcslen(greeting));
  15. // -----------------------布局模块结束----------------------------------
  16. EndPaint(hWnd, &ps);
  17. break;
  18. case WM_DESTROY:
  19. PostQuitMessage(0);
  20. break;
  21. default:
  22. //DefWindowProc缺省窗口处理函数
  23. //这个函数是默认的窗口处理函数,我们可以把不关心的消息都丢给它来处理
  24. return DefWindowProc(hWnd, message, wParam, lParam);
  25. break;
  26. }
  27. return 0;
  28. }

程序运行的结果为:

完整代码

到此我已经理清了写一个Windows应用程序的主要逻辑

我是按照Microsoft官方文档进行的学习,详见创建Windows桌面应用程序

对于更多的细节,代码中给出了详细注释。

[cpp] 
view plain
 copy

  1. // GT_HelloWorldWin32.cpp
  2. // compile with: /D_UNICODE /DUNICODE /DWIN32 /D_WINDOWS /c
  3. // 这是一个最简单的Win32程序,亦可作为开发桌面应用程序的模板
  4. #include <windows.h>
  5. #include <stdlib.h>
  6. #include <string.h>
  7. #include <tchar.h>
  8. // ------------------------Global variables---------------------------------
  9. // 主窗体类名
  10. static TCHAR szWindowClass[] = _T(“win32app”);
  11. // 应用程序标题栏处出现的字符串
  12. static TCHAR szTitle[] = _T(“Win32 Guided Tour Application”);
  13. //HINSTANCE 是Windows里的一中数据类型,是用于标示(记录)一个程序的实例。
  14. //它与HMODULE是一样的(通用的,这两种类型最终就是32位无符号长整形)。
  15. //HINSTANCE,分开看就是 HANDLE(句柄) + INSTANCE(实例)
  16. //实例就是一个程序。用qq来举例:你可以开同时开2个qq号,但是你电脑里的qq软件只有一份。
  17. //这2个qq号就是qq的2个实例
  18. HINSTANCE hInst;
  19. // -------------------------需要预定义的函数放置在此代码块种:----------------------------
  20. //每个 Windows 桌面应用程序必须具有一个窗口过程函数
  21. //此函数处理应用程序从操作系统中接收的大量消息。
  22. //例如,如果应用程序的对话框中有“确定”按钮,那么用户单击该按钮时,
  23. //操作系统会向应用程序发送一条消息,通知按钮已被单击。WndProc 负责对该事件作出响应。
  24. //在本例中,相应的响应可能是关闭对话框。
  25. LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
  26. //-------------------------------------正式内容-----------------------------------------
  27. //主窗体函数(入口过程)
  28. //每个基于 Win32 的应用程序的函数必须具有 WinMain 函数
  29. //正如每个 C 应用程序和 C++ 控制台应用程序在起始点必须具有 main 函数
  30. int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) {
  31. //创建 WNDCLASSEX 类型的窗口类结构。 此结构包含关于窗口的信息
  32. //例如应用程序图标、窗口背景色、标题栏中显示的名称、窗口过程函数的名称等。
  33. WNDCLASSEX wcex;
  34. wcex.cbSize = sizeof(WNDCLASSEX);
  35. wcex.style          = CS_HREDRAW | CS_VREDRAW;
  36. wcex.lpfnWndProc    = WndProc;
  37. wcex.cbClsExtra     = 0;
  38. wcex.cbWndExtra     = 0;
  39. wcex.hInstance      = hInstance;
  40. wcex.hIcon          = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_APPLICATION));
  41. wcex.hCursor        = LoadCursor(NULL, IDC_ARROW);
  42. wcex.hbrBackground  = (HBRUSH)(COLOR_WINDOW+1);
  43. wcex.lpszMenuName   = NULL;
  44. wcex.lpszClassName  = szWindowClass;
  45. wcex.hIconSm        = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_APPLICATION));
  46. //对已创建的窗口类进行注册。 使用 RegisterClassEx 函数,并将窗口类结构作为参数传递。
  47. if (!RegisterClassEx(&wcex)) {
  48. MessageBox(NULL, _T(“Call to RegisterClassEx failed!”), _T(“Win32 Guided Tour”), NULL);
  49. return 1;
  50. }
  51. // Store instance handle in our global variable
  52. // 将句柄实例存储于全局变量中
  53. hInst = hInstance;
  54. // CreateWindow 函数的参数解释:
  55. // szWindowClass: the name of the application
  56. // szTitle: the text that appears in the title bar
  57. // WS_OVERLAPPEDWINDOW: the type of window to create
  58. // CW_USEDEFAULT, CW_USEDEFAULT: initial position (x, y)
  59. // 500, 100: initial size (width, length)
  60. // NULL: the parent of this window
  61. // NULL: this application does not have a menu bar
  62. // hInstance: the first parameter from WinMain
  63. // NULL: not used in this application
  64. // 返回的HWND是一个窗口的句柄
  65. HWND hWnd = CreateWindow( szWindowClass, szTitle, WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, 500, 100, NULL, NULL, hInstance, NULL );
  66. if (!hWnd) {
  67. MessageBox(NULL, _T(“Call to CreateWindow failed!”), _T(“Win32 Guided Tour”), NULL);
  68. return 1;
  69. }
  70. // ShowWindow 函数的参数解释:
  71. // hWnd: CreateWindow函数返回的窗口句柄
  72. // nCmdShow: the fourth parameter from WinMain
  73. ShowWindow(hWnd, nCmdShow);
  74. // UpdateWindow函数用于更新窗口指定的区域
  75. // 如果窗口更新的区域不为空,UpdateWindow函数就发送一个WM_PAINT消息来更新指定窗口的客户区。
  76. // 函数绕过应用程序的消息队列,直接发送WM_PAINT消息给指定窗口的窗口过程
  77. // 如果更新区域为空,则不发送消息。
  78. UpdateWindow(hWnd);
  79. // Main message loop:
  80. // 添加用于侦听操作系统所发送消息的消息循环。
  81. // 当应用程序收到一条消息时,此循环将该消息调度到 WndProc 函数以进行处理。
  82. MSG msg;
  83. while (GetMessage(&msg, NULL, 0, 0)) {
  84. TranslateMessage(&msg); //翻译消息
  85. DispatchMessage(&msg);  //派遣消息
  86. }
  87. return (int) msg.wParam;
  88. }
  89. // //  函数: WndProc(HWND, UINT, WPARAM, LPARAM)
  90. // //  目标:  处理主窗体产生的信息
  91. // //  WM_PAINT消息代表绘制主窗体
  92. // //  WM_DESTROY消息代表投递一个退出消息并返回
  93. LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) {
  94. PAINTSTRUCT ps;
  95. HDC hdc;
  96. TCHAR greeting[] = _T(“Hello, World!”);
  97. switch (message) {
  98. case WM_PAINT:
  99. //要处理 WM_PAINT 消息,首先应调用 BeginPaint
  100. //然后处理所有的逻辑以及在窗口中布局文本、按钮和其他控件等
  101. //然后调用 EndPaint。
  102. hdc = BeginPaint(hWnd, &ps);
  103. // -----------------在这段代码对应用程序进行布局------------------------
  104. // 对于此应用程序,开始调用和结束调用之间的逻辑是在窗口中显示字符串 “Hello,World!”。
  105. // 请注意 TextOut 函数用于显示字符串。
  106. TextOut(hdc, 50, 5, greeting, _tcslen(greeting));
  107. // -----------------------布局模块结束----------------------------------
  108. EndPaint(hWnd, &ps);

img
img

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化的资料的朋友,可以添加戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

外链图片转存中…(img-BHhFKKzB-1715804260121)]

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化的资料的朋友,可以添加戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

  • 13
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值