日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

深入浅出MFC:动态创建控件

發(fā)布時(shí)間:2023/12/9 编程问答 37 豆豆
生活随笔 收集整理的這篇文章主要介紹了 深入浅出MFC:动态创建控件 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

——-先以CButton為例講解MFC中動(dòng)態(tài)創(chuàng)建控件———
在對(duì)話框類中增加了以下3個(gè)成員變量:
CButton m_btn1;
CButton m_btn2;
CButton m_btn3;

在對(duì)話框的OnInitDialog函數(shù)中寫入了如下代碼動(dòng)態(tài)創(chuàng)建控件

BOOL OnInitDialog {m_btn1.CreateEx(0, TEXT("BUTTON"), TEXT("Btn_1"), WS_CHILD | WS_VISIBLE, 10, 10, 100, 20,this->GetSafeHwnd(), (HMENU)IDC_BTN_DYN_BEG, 0);m_btn2.CreateEx(0, TEXT("BUTTON"), NULL, WS_CHILD | WS_VISIBLE, 10, 40, 100, 20,this->GetSafeHwnd(), (HMENU)IDC_BTN_DYN_BEG+1, 0);m_btn2.SetWindowText(TEXT("Btn_2"));m_btn3.Create(TEXT("Btn_3"), WS_CHILD | WS_VISIBLE, CRect(10, 70, 110, 90), this, IDC_BTN_DYN_BEG+4); }

我們現(xiàn)在來研究一下代碼的本質(zhì):
m_btn1.CreateEx與m_btn2.CreateEx實(shí)際上調(diào)用的CWnd::CreateEx
m_btn3.Create調(diào)用了CButton::Create
先來瞧瞧CButton::Create,其中調(diào)用了CWnd::Create

BOOL CButton::Create(LPCTSTR lpszCaption, DWORD dwStyle,const RECT& rect, CWnd* pParentWnd, UINT nID) {CWnd* pWnd = this;return pWnd->Create(_T("BUTTON"), lpszCaption, dwStyle, rect, pParentWnd, nID); }

CWnd::Create調(diào)用了CWnd::CreateEx

BOOL CWnd::Create(LPCTSTR lpszClassName,LPCTSTR lpszWindowName, DWORD dwStyle,const RECT& rect,CWnd* pParentWnd, UINT nID,CCreateContext* pContext) {return CreateEx(0, lpszClassName, lpszWindowName,dwStyle | WS_CHILD,rect.left, rect.top,rect.right - rect.left, rect.bottom - rect.top,pParentWnd->GetSafeHwnd(), (HMENU)(UINT_PTR)nID, (LPVOID)pContext); }

研究CWnd::CreateEx才能看出本質(zhì)

[wincore.cpp]

BOOL CWnd::CreateEx(DWORD dwExStyle, LPCTSTR lpszClassName,LPCTSTR lpszWindowName, DWORD dwStyle,int x, int y, int nWidth, int nHeight,HWND hWndParent, HMENU nIDorHMenu, LPVOID lpParam) {CREATESTRUCT cs;cs.dwExStyle = dwExStyle;cs.lpszClass = lpszClassName;cs.lpszName = lpszWindowName;cs.style = dwStyle;cs.x = x;cs.y = y;cs.cx = nWidth;cs.cy = nHeight;cs.hwndParent = hWndParent;cs.hMenu = nIDorHMenu;cs.hInstance = AfxGetInstanceHandle();cs.lpCreateParams = lpParam;if (!PreCreateWindow(cs)){PostNcDestroy();return FALSE;}AfxHookWindowCreate(this); //利用Hook進(jìn)行了子類化HWND hWnd = ::AfxCtxCreateWindowEx(cs.dwExStyle, cs.lpszClass,cs.lpszName, cs.style, cs.x, cs.y, cs.cx, cs.cy,cs.hwndParent, cs.hMenu, cs.hInstance, cs.lpCreateParams);return TRUE; }

[wincore.cpp]

void AFXAPI AfxHookWindowCreate(CWnd* pWnd) {pThreadState->m_pWndInit == pWnd;if (pThreadState->m_hHookOldCbtFilter == NULL){pThreadState->m_hHookOldCbtFilter = ::SetWindowsHookEx(WH_CBT,_AfxCbtFilterHook, NULL, ::GetCurrentThreadId());}pThreadState->m_pWndInit = pWnd; }

[wincore.cpp]

LRESULT CALLBACK _AfxCbtFilterHook(int code, WPARAM wParam, LPARAM lParam) {pWndInit->Attach(hWnd);pWndInit->PreSubclassWindow();WNDPROC *pOldWndProc = pWndInit->GetSuperWndProcAddr();WNDPROC afxWndProc = AfxGetAfxWndProc();//改寫了窗口過程函數(shù)為MFC通用的窗口過程函數(shù)也即子類化oldWndProc = (WNDPROC)SetWindowLongPtr(hWnd, GWLP_WNDPROC,(DWORD_PTR)afxWndProc); if (oldWndProc != afxWndProc)*pOldWndProc = oldWndProc;pThreadState->m_pWndInit = NULL; }

所以動(dòng)態(tài)創(chuàng)建控件全部都進(jìn)行了子類化
以下列出了MFC中具體控件對(duì)應(yīng)的窗口類名稱
(由于BUTTON按鈕對(duì)應(yīng)了PUSHBUTTON&CHECKBOX&RADIOBOX等,按鈕樣式區(qū)分了創(chuàng)建按鈕的類型)
顯然:
Button———- CButton—— “BUTTON” — BS_PUSHBUTTON
Check Box——- CButton—— “BUTTON” — BS_AUTOCHECKBOX
Radio Button—- CButton—— “BUTTON” — BS_AUTORADIOBUTTON
Edit Control—- CEdit——– “EDIT”
Combo Box——- CComboBox—- “COMBOBOX”
List Box——– CListBox—– “SysListView32”

如果要?jiǎng)討B(tài)創(chuàng)建Check Box,代碼如下

CButton m_btnChk; m_btnChk.CreateEx(0, TEXT("BUTTON"), NULL, WS_CHILD | WS_VISIBLE | BS_AUTOCHECKBOX, 10, 160, 100, 20,this->GetSafeHwnd(), (HMENU)1250, 0);

在CButton實(shí)例對(duì)象調(diào)用CreateEx時(shí)指定窗口類名為”EDIT”都可以,只不過創(chuàng)建的控件就是Edit Box了

m_btn1.CreateEx(0, TEXT("EDIT"), TEXT("Btn_1"), WS_CHILD | WS_VISIBLE, 10, 10, 100, 20,this->GetSafeHwnd(), (HMENU)IDC_BTN_DYN_BEG, 0);

總結(jié)

以上是生活随笔為你收集整理的深入浅出MFC:动态创建控件的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。