标签:mfc
一个MFC程序启动机制。 AFX_MODULE_STATE* pModuleState = _AFX_CMDTARGET_GETSTATE(); aaa//当前程序模块信息 class AFX_MODULE_STATE : public CNoTrackObject #ifdef _AFXDLL #define _AFX_CMDTARGET_GETSTATE() (m_pModuleState) #else #define _AFX_CMDTARGET_GETSTATE() (AfxGetModuleState()) #endif CMyWinApp theApp{ AFX_MODULE_STATE* pModuleState = _AFX_CMDTARGET_GETSTATE();//获取全局变量模块状态aaa AFX_MODULE_THREAD_STATE* pThreadState = pModuleState->m_thread;//获取全局变量线程状态信息bbb pThreadState->m_pCurrentWinThread = this; //将theApp地址赋值给aaa对象 } CWinThread* AFXAPI AfxGetThread() { // check for current thread in module thread state AFX_MODULE_THREAD_STATE* pState = AfxGetModuleThreadState(); //以Afx开头的都是全局的获取全局变量BBB的地址 CWinThread* pThread = pState->m_pCurrentWinThread; //CMyWinApp-->CWinApp-->CWinThread-->CCmdTarget-->CObject //基类指针指向孙子类 // if no CWinThread for the module, then use the global app if (pThread == NULL) pThread = AfxGetApp(); return pThread; } _AFXWIN_INLINE CWinApp* AFXAPI AfxGetApp() //获取全局对象 { return afxCurrentWinApp; } #define afxCurrentWinApp AfxGetModuleState()->m_pCurrentWinApp pThreadModule->m_pCurrentWinThread=this MFC第一大机制 MFC程序启动机制 第一个MFC程序 环境配置: 删除WinMain函数 将包含的头文件改为<afxwin.h> project->Settings中使用MFC库 代码编写 从CFrameWnd类派生自己的子类CMyFrameWnd 从CWinApp类派生自己的子类CMtWinApp 在CMyWinApp类内部重写父类的成员虚函数IninInstance 全局域中定义一个全局对象CMyWinApp theApp(爆破点) 程序执行过程: 1.mfc封装WinMain所以程序不需要实现 2.构造theApp全局对象,执行CWinApp类的构造函数 1)将theApp对象地址保存到当前程序模块状态信息中 2)将theApp对象地址保存到当前程序线程状态信息中 3)AfxGetThread/AfxGetApp --返回theApp对象地址 3.进入WinMain函数,其直接调用AfxWinMain函数 1)AfxWinMain执行过程 1)获取theApp地址 2)利用theApp对象地址调用InitApplication虚函数初始化MFC应用程序 3)利用theApp对象地址调用InitInstance虚函数,创建、显示、刷新 窗口 4)利用theApp对象设置调用Run虚函数,实现消息循环 5)程序退出时利用theApp对象地址调用ExiyInstance虚函数,善后处理。 应用程序类(CWinApp) 成员虚函数 InitApplication InitInstance OnIdel Run ExitInstance 成员变量 m_pMainWnd theApp --->m_pMainWnd MFC类库中没有对象,只有类 ********************************************************************** WinMain(...){ AfxWinMain(....){ CWinThread* pThread = AfxGetThread(); ////theApp地址 CWinApp* pApp = AfxGetApp(); ////theApp地址 //以上两句获取theApp对象地址 AfxWinInit(hInstance, hPrevInstance, lpCmdLine, nCmdShow) //初始化MFC库 pApp->InitApplication() //theApp-->虚函数 //重写后执行流程会改变,执行自己的函数 //实为CWinApp的 pThread->InitInstance() //回到自己写的代码 重写改变执行流程 //this指针为theApp对象地址.pThread值为theApp //InitInstance由pThread调用 nReturnCode = pThread->Run();{ //this==pThread==theApp还是theApp CWinThread::Run();{ //函数内部this指针为theApp地址 while(没有消息){ 空闲处理 ths->OnIdel(); //空闲处理 } PumpMessage(){ pump 打气筒,抽取 if(GetMessage抓到WM_QUIT){ return FALSE; } } if(PumpMessage返回FALSE){ ExitInstance();//应用程序类的虚函数,善后处理 } } } } } 一直由theApp对象指针调用虚函数 *************************************************************************** CMyWinApp theApp; BOOL CMyWinApp::InitInstance(){ //this======theApp CMyFrameWnd *pFrame=new CMyFrameWnd(); //框架类对象 pFrame->Create(NULL,"MyFrame"); //创建+注册 m_pMainWnd=pFrame; //this->m_pMainWnd保存框架类对象地址 pFrame->ShowWindow(SW_SHOW); //目测为CWinApp类的成员 pFrame->UpdateWindow(); //成员函数由theApp调用 return TRUE; } int CWinApp::Run() { if (m_pMainWnd == NULL && AfxOleGetUserCtrl()) { // Not launched /Embedding or /Automation, but has no main window! TRACE0("Warning: m_pMainWnd is NULL in CWinApp::Run - quitting application.\n"); AfxPostQuitMessage(0); //退出程序 } return CWinThread::Run(); this->CWinAppThread::Run(); } BOOL CWinThread::PumpMessage() { ASSERT_VALID(this); if (!::GetMessage(&m_msgCur, NULL, NULL, NULL)) { #ifdef _DEBUG if (afxTraceFlags & traceAppMsg) TRACE0("CWinThread::PumpMessage - Received WM_QUIT.\n"); m_nDisablePumpCount++; // application must die // Note: prevents calling message loop things in 'ExitInstance' // will never be decremented #endif return FALSE; } #ifdef _DEBUG if (m_nDisablePumpCount != 0) { TRACE0("Error: CWinThread::PumpMessage called when not permitted.\n"); ASSERT(FALSE); } #endif #ifdef _DEBUG if (afxTraceFlags & traceAppMsg) _AfxTraceMsg(_T("PumpMessage"), &m_msgCur); #endif // process this message if (m_msgCur.message != WM_KICKIDLE && !PreTranslateMessage(&m_msgCur)) { ::TranslateMessage(&m_msgCur); ::DispatchMessage(&m_msgCur); } return TRUE; } int CWinThread::Run() { ASSERT_VALID(this); // for tracking the idle time state BOOL bIdle = TRUE; LONG lIdleCount = 0; // acquire and dispatch messages until a WM_QUIT message is received. for (;;) { // phase1: check to see if we can do idle work while (bIdle && !::PeekMessage(&m_msgCur, NULL, NULL, NULL, PM_NOREMOVE)) //没消息时 //进入while循环 //::表示win32函数 { // call OnIdle while in bIdle state if (!OnIdle(lIdleCount++)) //this->OnIdel(空闲次数) OnIdel()前没有::,是成员函数 bIdle = FALSE; // assume "no idle" state } // phase2: pump messages while available do { // pump message, but quit on WM_QUIT if (!PumpMessage()) return ExitInstance(); //this->ExitInstance() theApp //应用程序类的成员虚函数 //点击关闭按钮出发的事件 // reset "no idle" state after pumping "normal" message if (IsIdleMessage(&m_msgCur)) { bIdle = TRUE; lIdleCount = 0; } } while (::PeekMessage(&m_msgCur, NULL, NULL, NULL, PM_NOREMOVE)); } ASSERT(FALSE); // not reachable } int AFXAPI AfxWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow) { ASSERT(hPrevInstance == NULL); int nReturnCode = -1; CWinThread* pThread = AfxGetThread(); ////theApp地址 CWinApp* pApp = AfxGetApp(); ////theApp地址 // AFX internal initialization if (!AfxWinInit(hInstance, hPrevInstance, lpCmdLine, nCmdShow)) //初始化MFC库 goto InitFailure; // App global initializations (rare) if (pApp != NULL && !pApp->InitApplication()) goto InitFailure; // Perform specific initializations if (!pThread->InitInstance()) { if (pThread->m_pMainWnd != NULL) { TRACE0("Warning: Destroying non-NULL m_pMainWnd\n"); pThread->m_pMainWnd->DestroyWindow(); } nReturnCode = pThread->ExitInstance(); goto InitFailure; } nReturnCode = pThread->Run(); InitFailure: #ifdef _DEBUG // Check for missing AfxLockTempMap calls if (AfxGetModuleThreadState()->m_nTempMapLock != 0) { TRACE1("Warning: Temp map lock count non-zero (%ld).\n", AfxGetModuleThreadState()->m_nTempMapLock); } AfxLockTempMaps(); AfxUnlockTempMaps(-1); #endif AfxWinTerm(); return nReturnCode; }
标签:mfc
原文地址:http://blog.csdn.net/u011185633/article/details/44775705