Windows圖形界面(GUI)-SDK-C/C++ - 應用程序結構

  • 公開視頻 ->?鏈接點擊跳轉公開課程
  • 博客首頁 ->?鏈接點擊跳轉博客主頁

目錄

入口函數

窗口注冊

窗口創建

窗口顯示

窗口更新

消息循環

窗口過程

窗口銷毀

調試信息

示例代碼


入口函數

  • 在Windows應用程序中,WinMain是主函數,作為應用程序的入口點。這與許多其他平臺上的main函數類似。
  • 函數原型
  • int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow);
    
  • 參數解析
    • HINSTANCE hInstance:當前實例的句柄(IMAGEBASE)。
    • HINSTANCE hPrevInstance:在32位Windows應用程序中,這個參數總是為NULL。在早期版本的Windows中,用于標識程序的前一個實例。
    • LPSTR lpCmdLine:指向一個以null終止的字符串,該字符串包含命令行參數。請注意,它不包含程序的名稱。
    • int nCmdShow:指定窗口如何顯示。

窗口注冊

  • 在Windows應用程序中,每個窗口都需要一個窗口類,這個類包含了窗口的屬性和一個事件處理函數(窗口過程)。要創建窗口,必須先注冊一個窗口類。
  • 函數原型
  • ATOM RegisterClassEx(const WNDCLASSEX *lpwcx);
    
  • 參數解析
    • lpwcx:指向WNDCLASSEX結構的指針,該結構包含了窗口類的信息。
    • WNDCLASSEX結構定義了窗口的特征,包括背景顏色、光標、圖標、菜單名和窗口過程等。
      • cbSize: 指定了結構體的大小,必須設置為 sizeof(WNDCLASSEX)
      • style: 類型的風格。可以是任何窗口類風格的組合,比如 CS_HREDRAWCS_VREDRAW
      • lpfnWndProc: 指向窗口過程的指針。這是一個函數指針,指向一個由系統調用以處理窗口消息的函數。
      • cbClsExtra: 指定分配給窗口類結構后面的額外字節數。通常這個值設為0。
      • cbWndExtra: 指定分配給每個窗口實例的額外字節數。例如,可以使用額外的空間存儲一個指向窗口數據的指針。
      • hInstance: 一個句柄,標識了包含窗口過程的應用程序實例。
      • hIcon: 一個圖標的句柄,這是與窗口類關聯的圖標。
      • hCursor: 一個光標的句柄,這是與窗口類關聯的光標。
      • hbrBackground: 設置窗口背景色的畫刷句柄。可以是一個顏色值的句柄,前面加上COLOR_的前綴。
      • lpszMenuName: 指向一個以 null 結束的字符串,該字符串指定類菜單,為資源名稱。如果使用類菜單,所有由該類創建的窗口都將使用這個菜單。
      • lpszClassName: 指向一個以 null 結束的字符串或是一個原子,如果此參數是一個原子,則它必須是一個全局原子。
      • hIconSm: 與窗口類關聯的小圖標的句柄。如果這個成員是 NULL,系統會從 hIcon 成員指定的大圖標中提取一個小圖標。

窗口創建

  • 注冊了窗口類之后,可以用CreateWindowEx函數創建窗口。
  • 函數原型
  • HWND CreateWindowEx(DWORD dwExStyle,LPCSTR lpClassName,LPCSTR lpWindowName,DWORD dwStyle,int X,int Y,int nWidth,int nHeight,HWND hWndParent,HMENU hMenu,HINSTANCE hInstance,LPVOID lpParam
    );
    
  • 函數參數
    • dwExStyle: 擴展窗口樣式。這些樣式控制各種擴展的窗口特征,例如帶有邊界陰影的窗口或者無邊框的窗口等。
    • lpClassName: 注冊的窗口類名。這可以是一個指向以 null 結尾的字符串的指針,或一個由 RegisterClassEx 函數返回的原子。
    • lpWindowName: 窗口的標題文字。如果窗口是一個控件,這個參數是一個指向以 null 結尾的字符串的指針,表示控件的文本。
    • dwStyle: 窗口的風格。這些風格控制著窗口的一般外觀和行為。
    • X: 窗口創建時水平位置的坐標。如果參數是 CW_USEDEFAULT,系統會選擇窗口的默認位置。
    • Y: 窗口創建時垂直位置的坐標。如果參數是 CW_USEDEFAULT,系統會選擇窗口的默認位置。
    • nWidth: 窗口的寬度。如果設置為 CW_USEDEFAULT,系統會選擇窗口的默認寬度。
    • nHeight: 窗口的高度。如果設置為 CW_USEDEFAULT,系統會選擇窗口的默認高度。
    • hWndParent: 父窗口句柄。如果沒有父窗口,此參數應為 NULL。彈出窗口和消息框將使用此參數指定的窗口作為它們的所有者。
    • hMenu: 窗口菜單句柄或子窗口標識符。如果是一個子窗口,此參數是一個菜單的句柄;如果是頂層窗口,此參數指定窗口的菜單;如果是子窗口,此參數是子窗口的標識符。
    • hInstance: 擁有窗口過程的應用程序的實例句柄。
    • lpParam: 指向一個值的指針,該值將被傳遞給窗口通過 WM_CREATE 消息。如果不需要傳遞值,此參數可以為 NULL

窗口顯示

  • ShowWindow函數設置窗口的顯示狀態。在一個窗口被創建后,它不會自動顯示;必須調用此函數來控制窗口的顯示。
  • 函數原型
  • BOOL ShowWindow(HWND hWnd,int  nCmdShow
    );
    
  • 函數參數
    • hWnd:窗口句柄,標識要設置顯示狀態的窗口。
    • nCmdShow:指定窗口如何被顯示。常用參數包括:
      • SW_SHOW:顯示窗口。
      • SW_HIDE:隱藏窗口,活動狀態給另一個窗口。
      • SW_MINIMIZE:最小化窗口,活動狀態給另一個窗口。
      • SW_RESTORE:激活并顯示窗口。如果窗口最小化或最大化,系統會將其恢復到原始尺寸和位置。
      • SW_SHOWMAXIMIZED:激活窗口并將其最大化。
      • SW_SHOWMINIMIZED:激活窗口并將其最小化。
      • SW_SHOWMINNOACTIVE:窗口最小化,類似SW_SHOWMINIMIZED,但窗口不被激活。

窗口更新

  • UpdateWindow函數用于更新客戶區的無效區域,即發送一個WM_PAINT消息給窗口過程,如果客戶區沒有無效區域,則不發送消息。
  • 函數原型
  • BOOL UpdateWindow(HWND hWnd
    );
    
  • 函數參數
    • hWnd:窗口句柄,標識要更新的窗口。
    • 該函數通常在ShowWindow后調用,以便立即更新窗口的客戶區而無需等待WM_PAINT消息的正常排隊。

消息循環

  • Windows應用程序是事件驅動的。在WinMain中,程序必須不斷檢查和處理消息。這就是所謂的消息循環或消息處理機制。每個GUI應用程序都有一個消息隊列,Windows操作系統使用它來存儲對該應用程序的所有輸入(如鼠標點擊、鍵盤輸入等)。
  • 示例代碼
  • while (GetMessage(&msg, NULL, 0, 0))
    {TranslateMessage(&msg);DispatchMessage(&msg);
    }
    
  • 函數解析
    • GetMessage從消息隊列檢索消息。如果沒有消息,它會等待,直到有消息為止。如果返回0,意味著接收到WM_QUIT消息,循環會結束。
    • TranslateMessage將虛擬鍵消息轉換為字符消息。
    • DispatchMessage將消息發送到窗口程序。

窗口過程

  • 窗口過程是一個函數,它處理發送到窗口的消息。每個窗口都有一個與之關聯的窗口過程。當事件發生(比如用戶點擊按鈕),Windows會將相應的消息發送到窗口過程。窗口過程根據消息的類型執行相應的操作,并返回結果。
  • LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
    • HWND hwnd: 窗口的句柄。
    • UINT uMsg: 消息的標識。
    • WPARAM wParam: 消息特定的附加信息。
    • LPARAM lParam: 消息特定的附加信息。
    • // 實現窗口過程函數
      LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) 
      {return DefWindowProc(hwnd, uMsg, wParam, lParam);
      }

窗口銷毀

  • 窗口的銷毀 通常通過調用DestroyWindow函數來完成。當窗口被銷毀后,Windows會發送WM_DESTROY消息給窗口過程,窗口過程可以在接收到此消息時執行清理操作。

調試信息

  • OutputDebugStringA 函數是 Windows API 中的一個函數,它用于將一個字符串輸出到調試器。
#include <windows.h>
#include <stdio.h>int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) 
{char buffer[256];int value1 = 42;int value2 = 100;// 使用 sprintf 格式化字符串sprintf_s(buffer, sizeof(buffer), "Value 1: %d, Value 2: %d\n", value1, value2);// 輸出格式化后的字符串到調試器OutputDebugStringA(buffer);return 0;
}

示例代碼

#include <Windows.h>LRESULT CALLBACK MainWindowProc (HWND, UINT, WPARAM, LPARAM);INT WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{// 注冊窗口WNDCLASSEX wndclass = { 0 };wndclass.cbSize = sizeof(WNDCLASSEX);wndclass.style = NULL;wndclass.lpfnWndProc = MainWindowProc;wndclass.cbClsExtra = NULL;wndclass.cbWndExtra = NULL;wndclass.hInstance = hInstance;wndclass.hIcon = NULL;wndclass.hCursor = NULL;wndclass.hbrBackground = (HBRUSH)COLOR_WINDOW;wndclass.lpszMenuName = NULL;wndclass.lpszClassName = TEXT("0xCC");wndclass.hIconSm = NULL;if (!RegisterClassEx(&wndclass)){MessageBox(NULL, TEXT("RegisterClassEx Failed"), TEXT("Error"), MB_OK);return 1;}// 創建窗口HWND hwnd = CreateWindowEx(WS_EX_CLIENTEDGE,TEXT("0xCC"),TEXT("CreateWindowEx"),WS_OVERLAPPEDWINDOW,CW_USEDEFAULT,CW_USEDEFAULT,960,540,NULL,NULL,hInstance,NULL);if (hwnd == NULL){MessageBox(NULL, TEXT("CreateWindowEx Failed"), TEXT("Error"), MB_OK);return 1;}// 顯示窗口ShowWindow(hwnd, SW_SHOWDEFAULT);// 更新窗口UpdateWindow(hwnd);// 消息處理MSG msg = { 0 };while (GetMessage(&msg, 0, 0, 0)){TranslateMessage(&msg);DispatchMessage(&msg);}return 0;
}// 窗口過程
LRESULT CALLBACK MainWindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{switch (uMsg){case WM_CREATE:{MoveWindow(hwnd, 0, 0, 500, 500, FALSE);CREATESTRUCT* Cs = (CREATESTRUCT*)lParam;break;}case WM_DESTROY:{PostQuitMessage(0);break;}case WM_SIZE:{TCHAR szBuffer[0xFF] = { 0 };wsprintf(szBuffer, TEXT("WM_SIZE -> %d %d\r\n"), HIWORD(lParam), LOWORD(lParam));OutputDebugString(szBuffer);break;}case WM_MOVE:{TCHAR szBuffer[0xFF] = { 0 };wsprintf(szBuffer, TEXT("WM_MOVE -> %d %d\r\n"), HIWORD(lParam), LOWORD(lParam));OutputDebugString(szBuffer);break;}case WM_LBUTTONDOWN:{TCHAR szBuffer[0xFF] = { 0 };wsprintf(szBuffer, TEXT("WM_LBUTTONDOWN -> %d %d\r\n"), HIWORD(lParam), LOWORD(lParam));OutputDebugString(szBuffer);break;}case WM_KEYDOWN:{TCHAR szBuffer[0xFF] = { 0 };wsprintf(szBuffer, TEXT("WM_KEYDOWN -> %d\r\n"), wParam);OutputDebugString(szBuffer);break;}default:return DefWindowProc(hwnd, uMsg, wParam, lParam);}}

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/42576.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/42576.shtml
英文地址,請注明出處:http://en.pswp.cn/web/42576.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

網格化監控:Eureka與分布式服務網格的協同監控

網格化監控&#xff1a;Eureka與分布式服務網格的協同監控 引言 在微服務架構中&#xff0c;服務網格技術提供了一種有效的方式來管理和監控服務間的通信。Eureka作為Netflix開源的服務發現框架&#xff0c;雖然本身不直接提供服務網格的監控功能&#xff0c;但可以與服務網格…

設計模式探索:適配器模式

1. 適配器模式介紹 1.1 適配器模式介紹 適配器模式&#xff08;adapter pattern&#xff09;的原始定義是&#xff1a;將一個類的接口轉換為客戶期望的另一個接口&#xff0c;適配器可以讓不兼容的兩個類一起協同工作。 適配器模式的主要作用是把原本不兼容的接口&#xff0c…

【Python_GUI】thinker布局管理——place方法

place方法可以設置組件的大小以及組件在容器中的精確位置&#xff0c;其參數及含義如下&#xff1a; 參數含義X設置組件距離窗口左側的水平距離y設置組件距離窗口頂部的垂直距離width設置組件的寬度height設置組件的高度relx設置組件距離窗口左側的相對距離&#xff0c;范圍為…

c++初階學習----入門(上)

大家好啊。最近學習了一點關于c的知識。這不就迫不及待的來與大家分享了嘛。但我這也是現學現賣所以咧。有很多遺落甚至不對的地方希望大家可以在評論區里面指出來。這樣也可以增加大家對知識的鞏固。 c語言與c的聯系 不知道大家看到c會不會不由自主的聯想到C語言啊。畢竟都是…

手機自帶錄屏在哪?6個軟件教你快速進行手機錄屏

手機自帶錄屏在哪&#xff1f;6個軟件教你快速進行手機錄屏 手機自帶的錄屏功能可以讓你輕松錄制屏幕上的內容&#xff0c;記錄游戲過程、制作教程或捕捉其他重要時刻。不同品牌的手機可能在不同位置提供錄屏功能。以下是一些常見的手機品牌及其錄屏功能位置&#xff0c;以及一…

【康復學習--LeetCode每日一題】724. 尋找數組的中心下標

題目&#xff1a; 給你一個整數數組 nums &#xff0c;請計算數組的 中心下標 。 數組 中心下標 是數組的一個下標&#xff0c;其左側所有元素相加的和等于右側所有元素相加的和。 如果中心下標位于數組最左端&#xff0c;那么左側數之和視為 0 &#xff0c;因為在下標的左側不…

運動愛好者的新選擇:哈氪聆光氣傳導耳機,輕巧又安全

平時不管是漫步街頭、騎行穿梭&#xff0c;還是乘坐公共交通時&#xff0c;我總是喜歡佩戴耳機&#xff0c;借此隔絕外部的喧囂&#xff0c;享受音樂的樂趣。在戶外使用耳機&#xff0c;我更傾向于選擇氣傳導耳機&#xff0c;它們更符合我的需求&#xff0c;因為這種耳機能讓我…

優雅下線的藝術:Eureka服務管理深度解析

優雅下線的藝術&#xff1a;Eureka服務管理深度解析 引言 在微服務架構中&#xff0c;服務的動態注冊與發現是保證系統高可用性的關鍵。Eureka作為Netflix開源的服務發現框架&#xff0c;提供了服務注冊與發現的基本功能。然而&#xff0c;服務在下線時如何做到"優雅&qu…

每日一編程,早點拿offer

計算字符串最后一個單詞的長度&#xff0c;單詞以空格隔開 輸入描述&#xff1a; 輸入一行&#xff0c;代表要計算的字符串&#xff0c;非空 輸出描述&#xff1a; 輸出一個整數&#xff0c;表示輸入字符串最后一個單詞的長度。 輸入&#xff1a;hello world輸出&#xff1a…

kubernetes集群證書過期問題解決

kubernetes集群證書過期問題解決 問題描述檢查證書是否過期更新證書master節點操作node節點操作 問題描述 K8S 各個組件需要與 api-server 進行通信&#xff0c;通信使用的證書都存放在 /etc/kubernetes/pki 路徑下&#xff0c;kubeadm 生成的證書大部分默認有效期為 1 年&…

SECS/GEM快速完成半導體設備通訊

金南瓜幫助國內大量從事半導體前道設備開發研制、生產的設備廠商&#xff0c;通過快速提供穩定可靠的SECS/GEM、GEM300產品&#xff0c;為客戶在激光退火、濕法設備&#xff08;清洗、鍍膜等&#xff09;、離子注入、MOCVD、PVD等客戶專注于核心工藝提升&#xff0c;提升企業的…

`CyclicBarrier` 是 Java 中的一個同步輔助工具類,它允許一組線程相互等待,直到所有線程都達到了某個公共屏障點(barrier point)

CyclicBarrier 是 Java 中的一個同步輔助工具類&#xff0c;它允許一組線程相互等待&#xff0c;直到所有線程都達到了某個公共屏障點&#xff08;barrier point&#xff09;。當所有線程都到達屏障點時&#xff0c;它們可以繼續執行后續操作。CyclicBarrier 的特點是可以重復使…

中介子方程五十

XXFXXaXnXaXXαXLXyXXWXuXeXKXXiXyXΣXXΣXXVXuXhXXWXηXXiXhXXpXXhXiXXηXWXXhXuXVXXΣXXΣXyXiXXKXeXuXWXXyXLXαXXaXnXaXXFXXaXnXaXXαXLXyXXWXuXeXKXXiXyXΣXXΣXXVXuXhXXWXηXXiXhXXpXXhXiXXηXWXXhXuXVXXΣXXΣXyXiXXKXeXuXWXXyXLXαXXaXnXaXXFXXuXXWXXuXXdXXrXXαXXuXpX…

Gen4Gen:多概念個性化圖像生成的數據驅動革新

個性化文本到圖像生成模型在用戶控制生成過程方面取得了重要進展。這些模型能夠通過少量訓練樣本學習并合成包含新穎個性化概念的圖像&#xff0c;例如用戶的寵物或特定物品。然而&#xff0c;現有技術在處理多概念個性化時存在局限性&#xff0c;尤其是在生成包含多個相似概念…

連接與隔離:Facebook在全球化背景下的影響力

在當今全球化的背景下&#xff0c;Facebook作為全球最大的社交網絡平臺&#xff0c;不僅連接了世界各地的人們&#xff0c;還在全球社會、經濟和文化中發揮著深遠的影響。本文將深入探討Facebook在全球化進程中的作用&#xff0c;以及其對個體和社會之間連接與隔離的雙重影響。…

【續集】Java之父的退休之旅:從軟件殿堂到多彩人生的探索

Java之父的退休之旅&#xff1a;從軟件殿堂到多彩人生的探索-CSDN博客 四、科技領袖退休后的行業影響 4.1 傳承與啟迪 Gosling等科技領袖的退休&#xff0c;為行業內部年輕一代提供了更多的發展機會和成長空間。他們的退休不僅意味著權力和責任的交接&#xff0c;更是一種精…

等保測評新趨勢:應對數字化轉型中的安全挑戰

隨著信息技術的飛速發展&#xff0c;數字化轉型已成為企業提升競爭力、優化運營效率的重要手段。然而&#xff0c;這一轉型過程中&#xff0c;企業也面臨著前所未有的安全挑戰。等保測評&#xff08;信息安全等級保護測評&#xff09;作為保障信息系統安全的重要手段&#xff0…

html5路由如何在nginx上部署(vite+vue3)

我們知道前端常用的有Hash 模式和html5模式的路由&#xff0c;hash模式在nginx上部署不需要額外的操作&#xff0c;而html5模式則需要額外設置&#xff0c;這里介紹下如何在nginx根地址&#xff08;location / {}&#xff09;下部署和在非根地址上&#xff08;location /admin{…

【MATLAB源碼-第232期】基于matlab的 (204,188) RS編碼解碼仿真,采用QPSK調制輸出誤碼率曲線。

操作環境&#xff1a; MATLAB 2022a 1、算法描述 Reed-Solomon碼&#xff08;RS碼&#xff09;是一類廣泛應用于數字通信和存儲系統中的糾錯碼&#xff0c;尤其在光盤、衛星通信和QR碼等領域有著重要作用。RS碼是一種非二進制的糾刪碼&#xff0c;由Irving S. Reed和Gustave…

當CNN遇上Mamba,高性能與高效率通通拿下!

傳統視覺模型在處理大規模或高分辨率圖像時存在一定限制&#xff0c;為解決這個問題&#xff0c;研究者們就最近依舊火熱的Mamba&#xff0c;提出了Mamba結合CNN的策略。 這種結合可以讓Mamba在處理長序列數據時既能夠捕捉到序列中的時間依賴關系&#xff0c;又能夠利用CNN的局…