[原创]MFC框架程序WINMAIN函数分析(一)

MFC,竟然还不知道MFCMAIN函数在什么地方?怎么运行的?实在不高明。于是决定模仿JJHOU老师的方式,拿起手术刀,深入MFC的内部运行机制。但是俗话说,循序渐进。就是说在我们深入之前,首先要浅析一下… …

假如你用AppWizard一步一步NEXT下来,然后在CLASSVIEW中去找寻WINMAIN函数,那么你只有失望。MFC最大的特点是什么?封装!MFC的确封装的太好了,以至于很多想学习MFC的人都望而却步。闲话少说,还是继续我们今天的话题,MAIN函数!实话告诉你吧,即使你搜索所有的MFC生成的文件,都无法发现WINMAIN的字眼,那么它就近在什么地方呢?

我相信你已经想到,MAIN函数应该在主要的应用程序文件中。难道是“您定义的程序名.cpp”这个文件?不错就是它。再Crtl+F一下,看有没有我们要找的WINMAIN函数?看来你又要失望了,但是你主意有这样一句:

 

/

// The one and only CMy1App object

 

CMy1App theApp;   //本人建立的工程名为1

 

 

是不是很特别,再注意一下那句注释“The one and only CMy1App object”,每个应用程序有且只用一个CMy1App对象。我想你应该想到了,WinMain函数每个程序也只能有一个,那么这个全局对象跟WinMain函数肯定有莫大的关系?没错,相信你的直觉。

 

现在,我们该深入WinMain运行机制了。

首先,看看MFC的库文件把,它能给我们带来许多惊喜。(vc6的相应的目录是/Microsoft Visual Studio/VC98/MFC/SRCVC7相应的目录是/Microsoft Visual Studio .NET 2003/Vc7/atlmfc/src/mfc

首先应该看看CMy1App的基类,CWinApp的构造函数(在APPCORE.CPP中),找到以下内容:

 

CWinApp::CWinApp(LPCTSTR lpszAppName)

{

       if (lpszAppName != NULL)

              m_pszAppName = _tcsdup(lpszAppName);

       else

              m_pszAppName = NULL;

 

       // initialize CWinThread state

       AFX_MODULE_STATE* pModuleState = _AFX_CMDTARGET_GETSTATE();

       AFX_MODULE_THREAD_STATE* pThreadState = pModuleState->m_thread;

       ASSERT(AfxGetThread() == NULL);

       pThreadState->m_pCurrentWinThread = this;

       ASSERT(AfxGetThread() == this);

       m_hThread = ::GetCurrentThread();

       m_nThreadID = ::GetCurrentThreadId();

 

       // initialize CWinApp state

       ASSERT(afxCurrentWinApp == NULL); // only one CWinApp object please

       pModuleState->m_pCurrentWinApp = this;

       ASSERT(AfxGetApp() == this);

... ...

}

OK,就到这里就可以了。现在请注意:

pModuleState->m_pCurrentWinApp = this;

     这段代码的意思是,获得了CWinApp的全局对象的this指针。CWinApp之中的成员变量将因为theApp这个全局对象的诞生而获得配置和初始值。theApp配置完成以后,接下来就是今天的主角儿了,WinMain函数,打开appmodul.cpp

 

     _tWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,

       LPTSTR lpCmdLine, int nCmdShow)

{

       // call shared/exported WinMain

       return AfxWinMain(hInstance, hPrevInstance, lpCmdLine, nCmdShow);

}

 

然后再打开winmain.cpp

 

int AFXAPI AfxWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,

     LPTSTR lpCmdLine, int nCmdShow)

{

     ASSERT(hPrevInstance == NULL);

 

     int nReturnCode = -1;

     CWinThread* pThread = AfxGetThread();

     CWinApp* pApp = AfxGetApp();

 

     // AFX internal initialization

     if (!AfxWinInit(hInstance, hPrevInstance, lpCmdLine, nCmdShow))

            goto InitFailure;

 

     // App global initializations (rare)

     if (pApp != NULL && !pApp->InitApplication())

            goto InitFailure;

 

     // Perform specific initializations

     if (!pThread->InitInstance())

     {

            if (pThread->m_pMainWnd != NULL)

            {

                   TRACE(traceAppMsg,0,"Warning:Destroying non-NULL m_pMainWnd/n");

                   pThread->m_pMainWnd->DestroyWindow();

            }

            nReturnCode = pThread->ExitInstance();

            goto InitFailure;

     }

 

终于看到WinMain的真面目了,但是我们并不能满足,接下来,我们要了解他的运行机制,我们要知其然,更要知其所以然。只知其然,实在不高明!

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值