为什么在运行if (!ProcessShellCommand(cmdInfo))后出现 xxx.exe中的 0x5d1876e4 处最可能的异常: 0xC000

xzh1995 2014-02-18 10:06:36
BOOL CUIDemoApp::InitInstance()
{
// 如果一个运行在 Windows XP 上的应用程序清单指定要
// 使用 ComCtl32.dll 版本 6 或更高版本来启用可视化方式,
//则需要 InitCommonControlsEx()。否则,将无法创建窗口。
connPool= Connection_pool::GetInstance();
//InItDBConnPool(".","","","viewdb",5, 25);
exePath=(LPCSTR)AfxGetApp()->m_pszHelpFilePath;
CString str=AfxGetApp()->m_pszExeName;

exePath=exePath.substr(0,exePath.length()-str.GetLength()-4);
INITCOMMONCONTROLSEX InitCtrls;
InitCtrls.dwSize = sizeof(InitCtrls);
// 将它设置为包括所有要在应用程序中使用的
// 公共控件类。
InitCtrls.dwICC = ICC_WIN95_CLASSES;
InitCommonControlsEx(&InitCtrls);

CWinAppEx::InitInstance();

string path;
path=exePath+"Connect.ini";


CString ConnectTypeCS;
CString ConnectIPC;
CString ConnectPORTC;
GetPrivateProfileString(_T("Connect"),_T("ConnectType"),_T(""),ConnectTypeCS.GetBuffer(MAX_PATH),MAX_PATH,(LPCSTR)path.c_str());
GetPrivateProfileString(_T("Connect"),_T("IP"),_T(""),ConnectIPC.GetBuffer(MAX_PATH),MAX_PATH,(LPCSTR)path.c_str());
GetPrivateProfileString(_T("Connect"),_T("PORT"),_T(""),ConnectPORTC.GetBuffer(MAX_PATH),MAX_PATH,(LPCSTR)path.c_str());
GetPrivateProfileString(_T("Connect"),_T("ID"),_T(""),ipid.GetBuffer(MAX_PATH),MAX_PATH,(LPCSTR)path.c_str());
ConnectIP=ConnectIPC.GetBuffer(0);
ConnectIPC.ReleaseBuffer();
ConnectPORT=ConnectPORTC.GetBuffer(0);
ConnectPORTC.ReleaseBuffer();
ipid.ReleaseBuffer();
transform(ConnectType.begin(), ConnectType.end(), ConnectType.begin(), toupper);


CDlgLogon dlg;

int count = 0;

do
{
if(count >= 3)
{
::MessageBox(NULL, _T("三次登录尝试失败!"), _T("系统提示"), MB_OK);
return true;
}

dlg.m_user = _T("");
dlg.m_password = _T("");

dlg.m_ConnectType.Format(_T("%s"),ConnectTypeCS);
// =ConnectTypeCS;
dlg.m_IP.Format(_T("%s"),ConnectIP.c_str());
dlg.m_Port.Format(_T("%s"),ConnectPORT.c_str());;

if(dlg.DoModal() == IDOK)
{

if(ValidUser(dlg.m_user,dlg.m_password))
{



UserName=dlg.m_user;
WritePrivateProfileString(_T("Connect"),_T("ConnectType"),dlg.m_ConnectType,(LPCSTR)(LPCWSTR)path.c_str());
WritePrivateProfileString(_T("Connect"),_T("IP"),dlg.m_IP,(LPCSTR)(LPCWSTR)path.c_str());
WritePrivateProfileString(_T("Connect"),_T("PORT"),dlg.m_Port,(LPCSTR)(LPCWSTR)path.c_str());
ConnectType=dlg.m_ConnectType.GetBuffer(0);
dlg.m_ConnectType.ReleaseBuffer();
if (ConnectType=="SERVER")
{
ConnectPORT=dlg.m_Port.GetBuffer(0);
dlg.m_Port.ReleaseBuffer();
ServerConnect(ConnectPORT);

}
else
{


ConnectIP=dlg.m_IP.GetBuffer(0);
dlg.m_IP.ReleaseBuffer();
ConnectPORT=dlg.m_Port.GetBuffer(0);
dlg.m_Port.ReleaseBuffer();
ClientConnect(ConnectIP,ConnectPORT);
}

break;
}
else
{
count++;
}
}
else
{
return true;
}
}while(1);

// 初始化 OLE 库
if (!AfxOleInit())
{
AfxMessageBox(IDP_OLE_INIT_FAILED);
return FALSE;
}
AfxEnableControlContainer();

InitShellManager();//初始化CMFCShellTreeCtrl和CMFCShellListCtrl
// 标准初始化
// 如果未使用这些功能并希望减小
// 最终可执行文件的大小,则应移除下列
// 不需要的特定初始化例程
// 更改用于存储设置的注册表项
// TODO: 应适当修改该字符串,
// 例如修改为公司或组织名
//lbw
SetRegistryKey(_T("应用程序向导生成的本地应用程序"));
LoadStdProfileSettings(0); // 加载标准 INI 文件选项

InitContextMenuManager();


InitKeyboardManager();

InitTooltipManager();
CMFCToolTipInfo ttParams;
ttParams.m_bVislManagerTheme = TRUE;
theApp.GetTooltipManager()->SetTooltipParams(AFX_TOOLTIP_TYPE_ALL,RUNTIME_CLASS(CMFCToolTipCtrl), &ttParams);

// 注册应用程序的文档模板。文档模板
// 将用作文档、框架窗口和视图之间的连接
CSingleDocTemplate* pDocTemplate;
pDocTemplate = new CSingleDocTemplate(
IDR_MAINFRAME,
RUNTIME_CLASS(CUIDemoDoc),
RUNTIME_CLASS(CMainFrame), // 主 SDI 框架窗口
RUNTIME_CLASS(CAdminList));
if (!pDocTemplate)
return FALSE;
AddDocTemplate(pDocTemplate);
//CMainFrame cmainFrame;
//cmainFrame.OnQueryAdmin();

// 启用“DDE 执行”
EnableShellOpen();
RegisterShellFileTypes(TRUE);

// 分析标准外壳命令、DDE、打开文件操作的命令行
CCommandLineInfo cmdInfo;
ParseCommandLine(cmdInfo);


// 调度在命令行中指定的命令。如果
// 用 /RegServer、/Register、/Unregserver 或 /Unregister 启动应用程序,则返回 FALSE。
if (!ProcessShellCommand(cmdInfo))
return FALSE;

////////////////////////////////添加其他视图类
CView *pOldActiveView=((CFrameWnd*) m_pMainWnd)->GetActiveView();

CView *pNewActiveView=(CView*)GetDlgItem(AfxGetMainWnd()->m_hWnd,IDD_VIRTUALREPORT);

//通过这两行代码可以得到当前的view,并且根据nForm的id值,得到我们的view资源。

pNewActiveView=(CView*)new CVirtualReport();
CCreateContext context;

context.m_pCurrentDoc=pOldActiveView->GetDocument();

pNewActiveView->Create(NULL,NULL,WS_CHILD | WS_BORDER,CFrameWnd::rectDefault,m_pMainWnd,IDD_VIRTUALREPORT,&context);

pNewActiveView->OnInitialUpdate();

// 唯一的一个窗口已初始化,因此显示它并对其进行更新
m_pMainWnd->ShowWindow(SW_SHOW);
m_pMainWnd->UpdateWindow();
// 仅当具有后缀时才调用 DragAcceptFiles
// 在 SDI 应用程序中,这应在 ProcessShellCommand 之后发生
// 启用拖/放
m_pMainWnd->DragAcceptFiles();


//CWnd* LocalIp = GetDlgItem(IDC_EDIT_IP);
//LocalIp->SetWindowText(m_szServerIP);
return TRUE;
}
本来好好的 我加入了 连接sql server2008就报错 vs2008
...全文
392 9 打赏 收藏 转发到动态 举报
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
streamlet_h 2015-11-17
  • 打赏
  • 举报
回复
在奔溃时弹出来的对话框点重试,进去就可以看出是哪里出错了。我也遇到同样的问题,我的程序是加有ribbonbar的,出错的原因是有一个资源的图片被替换了,反正就是资源的问题造成的。
xzh1995 2014-02-19
  • 打赏
  • 举报
回复
引用 7 楼 xzh1995 的回复:
引用 4 楼 oyljerry 的回复:
把sql连接放到后面的地方,不放到InitInstance
我登录对话框放到什么地方
我放到OnCreate里面了 正在改
xzh1995 2014-02-19
  • 打赏
  • 举报
回复
引用 4 楼 oyljerry 的回复:
把sql连接放到后面的地方,不放到InitInstance
我登录对话框放到什么地方
xzh1995 2014-02-19
  • 打赏
  • 举报
回复
引用 5 楼 xianglitian 的回复:
[quote=引用 2 楼 xzh1995 的回复:] [quote=引用 1 楼 xianglitian 的回复:] 应该不是if (!ProcessShellCommand(cmdInfo))的问题 要不你删了试试
删了程序 还能跑 那是 他生成的[/quote]删除后好用了?[/quote]不行 后面继续报那个错 不能删
向立天 2014-02-19
  • 打赏
  • 举报
回复
引用 2 楼 xzh1995 的回复:
[quote=引用 1 楼 xianglitian 的回复:] 应该不是if (!ProcessShellCommand(cmdInfo))的问题 要不你删了试试
删了程序 还能跑 那是 他生成的[/quote]删除后好用了?
oyljerry 2014-02-18
  • 打赏
  • 举报
回复
把sql连接放到后面的地方,不放到InitInstance
xzh1995 2014-02-18
  • 打赏
  • 举报
回复
引用 1 楼 xianglitian 的回复:
应该不是if (!ProcessShellCommand(cmdInfo))的问题 要不你删了试试
删了程序 还能跑 那是 他生成的
向立天 2014-02-18
  • 打赏
  • 举报
回复
应该不是if (!ProcessShellCommand(cmdInfo))的问题 要不你删了试试
xzh1995 2014-02-18
  • 打赏
  • 举报
回复
谁了帮我解决下 非常感谢
什么是句柄? 句柄,是整个Windows编程的基础。一个句柄是指使用的一个唯一的整数值,即一个4字节(64位程序为8字节)长的数值,来标识应用程序的不同对象和同类对象的不同的实例,诸如,一个窗口,按钮,图标,滚动条,输出设备,控件或者文件等。应用程序能够通过句柄访问相应的对象的信息,但是句柄不是一个指针,程序不能利用句柄来直接阅读文件的信息。如果句柄不用在I/O文件,它是毫无用的。 句柄是Windows用来标志应用程序建立的或是使用的唯一整数,Windows使用了大量的句柄来标志很多对象。 一、MFC AppWizard 1、MFC(Microsoft Foundation Class,微软基础类库)是微软为了简化程序员的开发工作所开发的一套C++ 类的集合,是一套面向对象的函数库,以类的方式提供给用户使用 2、MFC AppWizard是一个辅助我们生成源代码的向导工具,它可以帮助我们自动生成基于MFC框架的源代码 二、基于MFC的程序框架剖析 1、MFC程序的ClassView标签页(图) 2、继承关系 (1)CMainFrame继承于CFrameWnd (2)CTestApp继承于CWinApp (3)CTestDoc继承于CDocument (4)CTestView继承于CView 注:CFrameWnd和CView都继承于CWnd 3、CWnd类是MFC一个非常重要的类,它封装了与窗口相关的操作 4、MFC类的简化组织结构图(图) 5、MFC程序也有一个WinMain函数,程序是在编译时,由链接器将它链接到程序 6、MFC程序具有一个CTestApp类的全局对象theApp,在MFC程序运行时,程序执行的顺序为:theApp全局对象定义 ->CTestApp构造函数->WinMain函数 7、对于普通的VC++控制台程序,无论全局变量还是全局对象,程序运行时,在加载main函数之前,就已经为它们 分配了内存空间。对于一个全局对象来说,此时就会调用该对象的构造函数,构造该对象,并进行初始化操作 8、实例句柄与全局对象 (1)对于Win32 SDK程序,应用程序的实例是由实例句柄(WinMain函数的hInstance参数)来标识的 (2)对于MFC程序,应用程序的实例是由全局对象(每一个MFC程序有且仅有一个从应用程序类CWinApp派生的类, 如CTestApp,它实例化theApp全局对象)来标识的 9、基类构造函数this指针的指向问题 在构造子类对象时,会自动调用父类的构造函数,此时在父类的构造函数的this指针所指向的是子类对象地址 10、AfxWinMain函数 MFC程序的WinMain函数是通过调用AfxWinMain函数来完成它的功能的 注:Afx前缀的函数代表应用程序框架(Application Framework)函数,它们可以在程序的任何地方被调用 11、CTestApp::InitInstance函数 在AfxWinMain函数,通过调用InitInstance函数来完成MFC内部管理方面的工作 12、AfxEndDeferRegisterClass函数 MFC提供了一些默认的标准窗口类,我们只需要选择所需的窗口类就行。然后,调用AfxEndDeferRegisterClass 函数来注册窗口类 13、CMainFrame::PreCreateWindow函数 MFC程序具有两个窗口(框架窗口和视类窗口),在框架窗口产生之前会调用PreCreateWindow函数 14、CWnd::CreateEx函数 在MFC程序,窗口的创建是由CreateEx函数实现的 15、CWnd::CreateWindowEx函数 主要作用是当修改了CreateEx函数的CREATESTRUCT参数时,CreateWindowEx函数会根据参数发生的相应变化来创 建一个符合我们要求的窗口 注:MFC后缀名为Ex的函数都是扩展函数 16、CMainFrame::ShowWindow函数和CMainFrame::UpdateWindow函数 用于显示应用程序框架窗口和更新这个窗口 17、CWinThread::Run函数和CWinThread::PumpMessage函数 用于完成消息循环 18、DefWindowProc函数 默认的窗口过程,但MFC程序对消息的理实际上是通过消息映射机制来完成的 19、MFC程序的运行过程 (1)首先利用全局应用程序对象theApp启动应用程序 (2)调用全局应用程序对象的构造函数,从而就会调用其基类CWinApp的构造函数,以完成应用程序的一些初始化 (3)进入WinMain函数 (4)进入消息循环 20、MFC程序的主要过程 theApp-> CTestApp::CTestApp构造函数-> CWinApp::CWinApp构造函数-> _tWinMain(WinMain函数的宏)-> AfxWinMain函数-> CTestApp::InitInstance函数-> AfxEndDeferRegisterClass函数-> CMainFrame::PreCreateWindow函数-> CFrameWnd::PreCreateWindow函数-> AfxDeferRegisterClass(AfxEndDeferRegisterClass函数的宏)-> CFrameWnd::Create函数-> CWnd::CreateEx函数-> CMainFrame::PreCreateWindow函数-> CWnd::CreateEx函数-> CMainFrame::ShowWindow函数-> CMainFrame::UpdateWindow函数-> CWinThread::Run函数-> CWinThread::PumpMessage函数 21、框架窗口(整个应用程序外框所包括的部分)是视类窗口(框架窗口空白的地方)的一个父窗口 22、MFC提供了一个文档/视类的结构,文档是指CDocument类,视类是指CView类。前者用于数据的存储和加载, 后者用于数据的显示和修改 23、框架对象、文档对象和视类对象是通过一个单文档模板指针来有机地组织在一起,并利用AddDocTemplate函数 把这个单文档模板添加到文档模板,从而把这三个类组织成为一个整体 24、MFC程序的CAboutDlg类继承于CDialog类,用于为用户提供一些与程序相关的帮助信息 三、窗口类、窗口类对象与窗口 1、以“::”开始的函数是一个全局函数,表示调用的是Platform SDK的函数 2、如果我们关闭了一个窗口,这个窗口就销毁了,那么该窗口对应的C++窗口类对象销毁了吗? (1)当一个窗口销毁时,它会调用CWnd::DestroyWindow函数,该函数销毁窗口后,将CWnd::m_hWnd设为NULL (2)窗口的生命周期和C++窗口类对象的声明周期不是一致的。当一个窗口销毁时,与C++窗口类对象没有关系,它 们之间的纽带仅仅在于这个C++窗口类内部的成员变量m_hWnd,该变量保存了与这个C++窗口类对象相关的哪个窗口 的句柄 (3)但是,当C++窗口类对象销毁时,与之相关的窗口也将销毁,因为它们之间的纽带m_hWnd已经断了 3、示例---在窗口显示按钮 (1)CButton按钮类继承于CWnd (2)对于一个CButton对象,在定义之后就可以使用了;但是,如果要显示这个按钮的话,还需调用 CButton::Create函数,把按钮窗口与CButton对象关联起来 (3)MFC程序的窗口创建时都会产生WM_CREATE消息,该消息通过OnCreate函数来捕获。对于框架窗口来说,MFC直 接把OnCreate函数提供到了CMainFrame;而在视类窗口没有提供该函数,如需使用,要用户自行添加 (4)通常对MFC程序的操作,都是在CTestView视类窗口进行的 (5)在窗口创建之后,要显示该窗口可以通过调用ShowWindow函数或指定窗口风格为WS_VISIBLE来实现 (6)实现过程 A:在CTestView类,添加CButton类型的私有成员m_btn B:在CTestView类,添加WM_CREATE消息的OnCreate理函数 C:在CTestView类,通过GetParent函数可以获得CMainFrame框架窗口对象的指针 D:实现一(在视类窗口通过ShowWindow函数显示按钮) int CTestView::OnCreate(LPCREATESTRUCT lpCreateStruct) { ... m_btn.Create("按钮",WS_CHILD|BS_DEFPUSHBUTTON,CRect(0,0,100,100),this,123); m_btn.ShowWindow(SW_SHOWNORMAL); return 0: } E:实现二(在视类窗口通过WS_VISIBLE风格显示窗口) int CTestView::OnCreate(LPCREATESTRUCT lpCreateStruct) { ... m_btn.Create("按钮",WS_CHILD|WS_VISIBLE|BS_DEFPUSHBUTTON,CRect(0,0,100,100),this,123); return 0: } F:实现三(在框架窗口显示按钮) int CTestView::OnCreate(LPCREATESTRUCT lpCreateStruct) { ... m_btn.Create("按钮",WS_CHILD|WS_VISIBLE|BS_DEFPUSHBUTTON,CRect(0,0,100,100),GetParent(),123); return 0: } 即便是基于MFC的应用程序,建立窗口类也是会遵循如下的过程: 设计窗口类->注册窗口类->生成窗口->显示窗口->更新窗口->消息循环->消息路由到窗口过程函数理。下面就剖析一下在MFC是如何完成上述过程的。 (1)每个应用程序都有且仅有一个应用类的全局变量theApp,全局变量先于WinMain函数进行理。 (2)WinMain函数体在APPMODUL.CPP文件,定义如下: extern "C" int WINAPI _tWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow) { // call shared/exported WinMain return AfxWinMain(hInstance, hPrevInstance, lpCmdLine, nCmdShow); } 其#define _tWinMain WinMain (3)AfxWinMain函数体在WINMAIN.CPP文件,里面有如下两句话: CWinThread* pThread = AfxGetThread(); CWinApp* pApp = AfxGetApp(); 其实这里得到的这两个指针都是指向全局的对象theApp的; 接下来有函数调用pThread->InitInstance(),根据多态性,会调用CXXXApp类的InitInstance()函数。该函数很重要,在对该函数的调用就会完成:设计窗口类->注册窗口类->生成窗口->显示窗口->更新窗口。 接下来,该函数会继续调用pThread->Run(),这就完成了:消息循环->消息路由到窗口过程函数理。 (4)进入CXXXApp::InitInstance()函数体,对于单文档应用程序,调用ProcessShellCommand(cmdInfo),通过调用该函数就会完成:设计窗口类->注册窗口类->生成窗口。 再接下来就会调用m_pMainWnd->ShowWindow(SW_SHOW);m_pMainWnd->UpdateWindow();这就完成了:显示窗口->更新窗口。 (5)在函数CWinApp::ProcessShellCommand(CCommandLineInfo& rCmdInfo)会进入到如下的case分支:case CCommandLineInfo::FileNew: if (!AfxGetApp()->OnCmdMsg(ID_FILE_NEW, 0, NULL, NULL)) (6)进入函数CCmdTarget::OnCmdMsg(UINT nID, int nCode, void* pExtra, AFX_CMDHANDLERINFO* pHandlerInfo),调用_AfxDispatchCmdMsg(this, nID, nCode, lpEntry->pfn, pExtra, lpEntry->nSig, pHandlerInfo); (7)进入函数AFXAPI _AfxDispatchCmdMsg(CCmdTarget* pTarget, UINT nID, int nCode, AFX_PMSG pfn, void* pExtra, UINT nSig, AFX_CMDHANDLERINFO* pHandlerInfo),调用 case AfxSig_vv: // normal command or control notification ASSERT(CN_COMMAND == 0); // CN_COMMAND same as BN_CLICKED ASSERT(pExtra == NULL); (pTarget->*mmf.pfn_COMMAND)(); (8)进入CWinApp::OnFileNew(),调用m_pDocManager->OnFileNew();这个函数很特殊,它本身是个消息响应函数,当我们点击ID为ID_FILE_NEW的菜单时,会产生一个命令消息,由于命令消息可以被CCmdTarget类及其派生类来捕获,而CWinApp是从CCmdTarget派生出来的,因此可以捕获这个消息。当应用程序创建完成并成功显示后,当我们点击文件菜单下的新建菜单项时,就会首先进入这个函数,然后再依次执行下去,最后就会执行到pDocument->OnNewDocument(),往往我们会对这个函数不解,不知道它为什么会响应ID_FILE_NEW的命令消息,至此真相大白了。顺便说一句,为什么程序在刚启动的时候,我们并没有点击菜单项,为什么会自动的产生这个消息呢?这是因为在CXXXXApp::InitInstance()函数有“CCommandLineInfo cmdInfo;”这个类的构造函数是这样的:CCommandLineInfo::CCommandLineInfo() { m_bShowSplash = TRUE; m_bRunEmbedded = FALSE; m_bRunAutomated = FALSE; m_nShellCommand = FileNew; },因此就会在第(5)步骤的时候进入到“case CCommandLineInfo::FileNew:”这个分支,就相当于产生了这样一个FileNew的消息。同理对于ID为ID_FILE_OPEN(在CWinApp::OnFileOpen()响应)、ID_FILE_SAVE(在CDocument::OnFileSave()响应)等等在MFC向导为我们生成的单文档类找不到消息响应的入口时,其实都是在基类CWinApp或者CDocument类进行了响应。对于CXXXXDoc::Serialize(CArchive& ar)函数也是通过ID_FILE_SAVE和ID_FILE_OPEN产生命令消息后就行响应从而才调用该函数的。 (9)进入CDocManager::OnFileNew(),CDocManager类有一个成员变量是CPtrList m_templateList;该变量保存了一个文档模版链表指针,在CDocManager::OnFileNew()函数体会调用CDocTemplate* pTemplate = (CDocTemplate*)m_templateList.GetHead();得到链表的头,也就是第一个文档模版,后面就会用得到的这个指针去调用pTemplate->OpenDocumentFile(NULL);紧接着就会有一个判断,用来确定该链表是否只有一项,如果链表保存了多个文档模版,则会弹出一个对话框,来让我们选择到底是使用哪一套文档模版来构建应用程序,相信大家也都见到过这种情况吧。对了,还有一点要说明的是:pTemplate是一个CDocTemplate的指针,但接下来程序为什么会进入到CSingleDocTemplate::OpenDocumentFile的函数体内呢,这是因为CDocTemplate类的OpenDocumentFile函数被定义为纯虚函数,而CSingleDocTemplate类又是从CDocTemplate类派生出来的,并且实现了该函数,因此就会进入到子类的函数体了。 (10)进入CDocument* CSingleDocTemplate::OpenDocumentFile(LPCTSTR lpszPathName, BOOL bMakeVisible),先调用CreateNewDocument()创建文档类,再调用pFrame = CreateNewFrame(pDocument, NULL);创建框架类和视图类,从这里也可以看出MFC体系结构文档、框架、视图“三位一体”的模式,在这一个函数同时创建三个类;再会调用pDocument->OnNewDocument();因此就会进入到子类的文档类的pDocument->OnNewDocument()了。 (11)进入CFrameWnd* CDocTemplate::CreateNewFrame(CDocument* pDoc, CFrameWnd* pOther),调用if (!pFrame->LoadFrame(m_nIDResource, WS_OVERLAPPEDWINDOW | FWS_ADDTOTITLE, // default frame styles NULL, &context)) (12)进入BOOL CFrameWnd::LoadFrame(UINT nIDResource, DWORD dwDefaultStyle, CWnd* pParentWnd, CCreateContext* pContext),调用VERIFY(AfxDeferRegisterClass(AFX_WNDFRAMEORVIEW_REG)); (13)进入BOOL AFXAPI AfxEndDeferRegisterClass(LONG fToRegister),该函数内部就完成了:设计窗口类->注册窗口类。MFC通过给我们提供好一些已经订制好的窗口类,我们不需要自己再设计窗口类,只需要到那些订制好的窗口类“仓库”寻找一种适合我们需要的窗口类就可以了,然后通过AfxRegisterClass函数注册窗口类。还需要说明的是,再后续的跟踪过程,我们会发现还会进入到AfxEndDeferRegisterClass函数进行设计和注册窗口类,这主要是因为单文档应用程序比较特殊,它提前通过这样的一种途径进行了窗口类的设计和注册步骤,其实是应该在BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs)函数的调用完成窗口类的设计和注册的,这一点我们要清楚,也就是说设计和注册窗口类的正宗发源地应该是PreCreateWindow(CREATESTRUCT& cs)。此外,我们还会注意到在该函数体的前部分有一语句为“wndcls.lpfnWndProc = DefWindowProc;”因此所有窗口类的窗口过程函数都是DefWindowProc,这一点在后面的跟踪可以看到,每次生成窗口之后都会调用几次DefWindowProc函数。也就是说MFC都是让我们采用默认的窗口过程函数,这并不是说我们因此就不能使用自己的窗口过程函数实现个性化的消息理了,MFC采用了一种基于消息映射的机制完成了消息个性化理。 (14)回到BOOL CFrameWnd::LoadFrame(UINT nIDResource, DWORD dwDefaultStyle, CWnd* pParentWnd, CCreateContext* pContext),调用LPCTSTR lpszClass = GetIconWndClass(dwDefaultStyle, nIDResource); (15)进入LPCTSTR CFrameWnd::GetIconWndClass(DWORD dwDefaultStyle, UINT nIDResource),调用PreCreateWindow(cs); (16)进入BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs),调用CFrameWnd::PreCreateWindow(cs) (17)进入BOOL CFrameWnd::PreCreateWindow(CREATESTRUCT& cs),调用VERIFY(AfxDeferRegisterClass(AFX_WNDFRAMEORVIEW_REG));又一次设计和注册窗口类 (18)回到BOOL CFrameWnd::LoadFrame(UINT nIDResource, DWORD dwDefaultStyle, CWnd* pParentWnd, CCreateContext* pContext),调用if (!Create(lpszClass, lpszTitle, dwDefaultStyle, rectDefault, pParentWnd, MAKEINTRESOURCE(nIDResource), 0L, pContext)) (19)进入BOOL CFrameWnd::Create(LPCTSTR lpszClassName, LPCTSTR lpszWindowName, DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, LPCTSTR lpszMenuName, DWORD dwExStyle, CCreateContext* pContext),调用if (!CreateEx(dwExStyle, lpszClassName, lpszWindowName, dwStyle, rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top, pParentWnd->GetSafeHwnd(), hMenu, (LPVOID)pContext)) (20)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),调用if (!PreCreateWindow(cs)) ,接下来调用HWND hWnd = ::CreateWindowEx(cs.dwExStyle, cs.lpszClass, cs.lpszName, cs.style, cs.x, cs.y, cs.cx, cs.cy, cs.hwndParent, cs.hMenu, cs.hInstance, cs.lpCreateParams);好了,终于让我们找到生成窗口的地方了——函数::CreateWindowEx! (21)进入int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct),调用if (CFrameWnd::OnCreate(lpCreateStruct) == -1) (22)进入int CFrameWnd::OnCreate(LPCREATESTRUCT lpcs),调用return OnCreateHelper(lpcs, pContext); (23)进入int CFrameWnd::OnCreateHelper(LPCREATESTRUCT lpcs, CCreateContext* pContext),调用if (CWnd::OnCreate(lpcs) == -1) (24)进入_AFXWIN_INLINE int CWnd::OnCreate(LPCREATESTRUCT),调用return (int)Default(); (25)进入LRESULT CWnd::Default(),调用return DefWindowProc(pThreadState->m_lastSentMsg.message, pThreadState->m_lastSentMsg.wParam, pThreadState->m_lastSentMsg.lParam); (26)进入LRESULT CWnd::DefWindowProc(UINT nMsg, WPARAM wParam, LPARAM lParam),调用return ::CallWindowProc(m_pfnSuper, m_hWnd, nMsg, wParam, lParam); (27)回到int CFrameWnd::OnCreateHelper(LPCREATESTRUCT lpcs, CCreateContext* pContext),调用if (!OnCreateClient(lpcs, pContext)) (28)进入BOOL CFrameWnd::OnCreateClient(LPCREATESTRUCT, CCreateContext* pContext),调用if (CreateView(pContext, AFX_IDW_PANE_FIRST) == NULL) (29)进入CWnd* CFrameWnd::CreateView(CCreateContext* pContext, UINT nID),调用if (!pView->Create(NULL, NULL, AFX_WS_DEFAULT_VIEW, CRect(0,0,0,0), this, nID, pContext)) (30)进入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)nID, (LPVOID)pContext); (31)进入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),重复生成框架类CMainFrame的过程来生成CXXXView,因为它也是一个窗口类,因此也需要进行那一系列过程才能最终显示更新出来。 调用的顺序是这个样子的:PreCreateWindow(cs)->BOOL CXXXView::PreCreateWindow(CREATESTRUCT& cs)->CView::PreCreateWindow(cs)->VERIFY(AfxDeferRegisterClass(AFX_WNDFRAMEORVIEW_REG));->::CreateWindowEx(...)->CWnd::DefWindowProc->::CallWindowProc(...)->...->CXXXView::OnCreate->CView::OnCreate->CWnd::OnCreate->... 写到这里,基本上就清楚了,间的省略号表示的部分大多数都是在与窗口过程函数有关的,因为在生成窗口的时候需要响应一些消息,因此需要调用一些窗口过程函数,每次在调用::CreateWindowEx(...)函数后都会调用一些窗口过程函数,然后再去调用该窗口类对应的OnCreate函数,其实在调用OnCreate函数之前调用CreateWindowEx只是生成了一个窗口,至于这个窗口里面要放置些什么东西,以及该如何装饰该窗口,则就需要由OnCreate来完成了,往往我们都会在OnCreate函数的后面(这样做是为了不影响窗口本身应该布置的格局)添加一些代码,创建我们自己的东西,比如我们通常会在CMainFrame类的OnCreate函数后面放置一些Create代码,来创建我们自己的可停靠的工具栏或者按钮之类的东西,当然我们也可以在CXXXView类的OnCreate函数的后面添加一些代码,来创建我们需要的东西,比如按钮之类的东西。在完成了从设计、注册到生成窗口的过程之后,往往还需要显示更新,有些时候,我们不必要每次都显示的调用CWnd的ShowWindow和UpdateWindow两个函数,我们可以在创建的时候,给窗口风格添加WS_VISIBLE即可,因此有些时候会跟踪不到ShowWindow和UpdateWindow两个函数这两个函数,因为窗口在创建的时候就可见了。 总的来说,先初始化应用类,然后注册生成框架类,然后再注册生成视图类,然后注册生成视图类OnCreate函数后面用户添加的、用Create来准备创建的窗口,然后再注册生成框架类的OnCreate函数后面需要生成的m_wndToolBar、m_wndStatusBar以及我们自己添加的要创建的窗口类,最后在回到应用类的初始化的函数体,调用框架类的显示和更新函数,然后再进入由框架类定义的窗口的消息循环。 消息循环的过程是这个样子的: (1)调用int AFXAPI AfxWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow)函数的pThread->Run() (2)进入int CWinApp::Run(),调用return CWinThread::Run(); (3)进入int CWinThread::Run(),调用if (!PumpMessage()) (4)进入BOOL CWinThread::PumpMessage(),调用if (!::GetMessage(&m_msgCur, NULL, NULL, NULL)) (5)回到BOOL CWinThread::PumpMessage(),调用::TranslateMessage(&m_msgCur);::DispatchMessage(&m_msgCur); (6)回到int CWinThread::Run(),调用while (::PeekMessage(&m_msgCur, NULL, NULL, NULL, PM_NOREMOVE)); (7)再重复(4)-(6)的步骤 下面给出int CWinThread::Run()消息循环的部分代码: do { // pump message, but quit on WM_QUIT if (!PumpMessage()) return ExitInstance(); // 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)); 这段代码其实本质上与我们基于Win32 SDK手写的代码: //消息循环 MSG msg; while(GetMessage(&msg,NULL,0,0)) { //简单的说,函数TranslateMessage就是把WM_KEYDOWN和WM_KEYUP翻译成WM_CHAR消息,没有该函数就不能产生WM_CHAR消息。 TranslateMessage(&msg); ::DispatchMessage(&msg); } 是一致的。 1,寻找WinMain人口: 在安装目录下找到MFC文件夹下的SRC文件夹,SRC下是MFC源代码。 路径:MFC|SRC|APPMODUL.CPP: _tWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow) { // call shared/exported WinMain return AfxWinMain(hInstance, hPrevInstance, lpCmdLine, nCmdShow); } 注意:(#define _tWinMain WinMain) 2,对于全局对象或全局变量来说,在程序运行即WINMAIN函数加载的时候,已经为全局对象或全局变量分配了内存和赋初值。 所以:CTEApp theApp;->CTEApp ::CTEApp(){}->_tWinMain(){} 说明:每一个MFC程序,有且只有一个从WinApp类派生的类(应用程序类),也只有一个从应用程序类所事例化的对象,表示应用程序本身。在WIN32程序当,表示应用程序是通过WINMAIN入口函数来表示的(通过一个应用程序的一个事例号这一个标识来表示的)。在基于MFC应用程序,是通过产生一个应用程序对象,用它来唯一的表示了应用程序。 3,通过构造应用程序对象过程调用基类CWinApp的构造函数,在CWinApp的构造函数对程序包括运行时一些初始化工作完成了。 CWinApp构造函数:MFC|SRC|APPCORE.CPP CWinApp::CWinApp(LPCTSTR lpszAppName){...}//带参数,而CTEApp构造函数没有显式向父类传参,难道CWinApp()有默认参数?见下: (在CWinApp类定义, CWinApp(LPCTSTR lpszAppName = NULL); ) 注意:CWinApp()函数: pThreadState->m_pCurrentWinThread = this; pModuleState->m_pCurrentWinApp = this (this指向的是派生类CTEApp对象,即theApp) 调试:CWinApp::CWinApp();->CTEApp theApp;(->CTEApp ::CTEApp())->CWinApp::CWinApp()->CTEApp ::CTEApp()->_tWinMain(){} 4,_tWinMain函数通过调用AfxWinMain()函数来完成它要完成的功能。(Afx*前缀代表这是应用程序框架函数,是一些全局函数,应用程序框架是一套辅助生成应用程序的框架模型,把一些类做一些有机的集成,我们可根据这些类函数来设计自己的应用程序)。 AfxWinMain()函数路径:MFC|SRC|WINMAIN.CPP: 在AfxWinMain()函数: CWinApp* pApp = AfxGetApp(); 说明:pApp存储的是指向WinApp派生类对象(theApp)的指针。 //_AFXWIN_INLINE CWinApp* AFXAPI AfxGetApp() // { return afxCurrentWinApp; } 调用pThread->InitInstance() 说明:pThread也指向theApp,由于基类virtual BOOL InitApplication()定义为虚函数,所以调用pThread->InitInstance()时候,调用的是派生类CTEApp的InitInstance()函数。 nReturnCode = pThread->Run(); 说明:pThread->Run()完成了消息循环。 5,注册窗口类:AfxEndDeferRegisterClass(); AfxEndDeferRegisterClass()函数所在文件:MFC|SRC|APPCORE.CPP BOOL AFXAPI AfxEndDeferRegisterClass(LONG fToRegister){...} 说明:设计窗口类:在MFC事先设计好了几种缺省的窗口类,根据不同的应用程序的选择,调用AfxEndDeferRegisterClass()函数注册所选择的窗口类。 调试:CWinApp::CWinApp();->CTEApp theApp;(->CTEApp ::CTEApp())->CWinApp::CWinApp()->CTEApp ::CTEApp()->_tWinMain(){}//进入程序 ->AfxWinMain();->pApp->InitApplication();->pThread->InitInstance()//父类InitInstance虚函数;->CTEApp::InitInstance()//子类实现函数;->AfxEndDeferRegisterClass(LONG fToRegister)//注册所选择的窗口类(出于文档管理,注册提前,正常的应在PreCreateWindow进行注册)//之后进入创建窗口阶段(以下再不做调试) 6,PreCreateWindow()://主要是注册窗口类 BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs) { if( !CFrameWnd::PreCreateWindow(cs) ) return FALSE; return TRUE; } 说明: CFrameWnd::PreCreateWindow()函数所在文件:MFC|SRC|WINFRM.CPP BOOL CFrameWnd::PreCreateWindow(CREATESTRUCT& cs) { if (cs.lpszClass == NULL) { VERIFY(AfxDeferRegisterClass(AFX_WNDFRAMEORVIEW_REG)); //判断AFX_WNDFRAMEORVIEW_REG型号窗口类是否注册,如果没有注册则注册 cs.lpszClass = _afxWndFrameOrView; // COLOR_WINDOW background //把注册后的窗口类名赋给cs.lpszClass } if ((cs.style & FWS_ADDTOTITLE) && afxData.bWin4) cs.style |= FWS_PREFIXTITLE; if (afxData.bWin4) cs.dwExStyle |= WS_EX_CLIENTEDGE; return TRUE; } 其: virtual BOOL PreCreateWindow(CREATESTRUCT& cs);//PreCreateWindow()是个虚函数,如果子类有则调用子类的。 #define VERIFY(f) ASSERT(f) #define AfxDeferRegisterClass(fClass) AfxEndDeferRegisterClass(fClass) define AFX_WNDFRAMEORVIEW_REG 0x00008 const TCHAR _afxWndFrameOrView[] = AFX_WNDFRAMEORVIEW;//WINCORE.CPP文件,定义为全局数组。 //#define AFX_WNDFRAMEORVIEW AFX_WNDCLASS("FrameOrView") 7,创建窗口: Create()函数路径:MFC|SRC|WINFRM.CPP: CFrameWnd::Create(...){ ... CreateEx(...);//从父类继承来的,调用CWnd::CreateEx(). ... } CWnd::CreateEx()函数路径:MFC|SRC|WINCORE.CPP BOOL CWnd::CreateEx(...){ ... if (!PreCreateWindow(cs))//虚函数,如果子类有调用子类的。 { PostNcDestroy(); return FALSE; } ... HWND hWnd = ::CreateWindowEx(cs.dwExStyle, cs.lpszClass, cs.lpszName, cs.style, cs.x, cs.y, cs.cx, cs.cy, cs.hwndParent, cs.hMenu, cs.hInstance, cs.lpCreateParams); ... } 说明:CreateWindowEx()函数与CREATESTRUCT结构体参数的对应关系,使我们在创建窗口之前通过可PreCreateWindow(cs)修改cs结构体成员来修改所要的窗口外观。PreCreateWindow(cs))//是虚函数,如果子类有调用子类的。 HWND CreateWindowEx( DWORD dwExStyle, LPCTSTR lpClassName, LPCTSTR lpWindowName, DWORD dwStyle, int x, int y, int nWidth, int nHeight, HWND hWndParent, HMENU hMenu, HINSTANCE hInstance, LPVOID lpParam ); typedef struct tagCREATESTRUCT { // cs LPVOID lpCreateParams; HINSTANCE hInstance; HMENU hMenu; HWND hwndParent; int cy; int cx; int y; int x; LONG style; LPCTSTR lpszName; LPCTSTR lpszClass; DWORD dwExStyle; } CREATESTRUCT; 8,显示和更新窗口: CTEApp类,TEApp.cpp m_pMainWnd->ShowWindow(SW_SHOW);//显示窗口,m_pMainWnd指向框架窗口 m_pMainWnd->UpdateWindow();//更新窗口 说明: class CTEApp : public CWinApp{...} class CWinApp : public CWinThread{...} class CWinThread : public CCmdTarget { ... public: CWnd* m_pMainWnd; ... ... } 9,消息循环: int AFXAPI AfxWinMain() { ... // Perform specific initializations if (!pThread->InitInstance()){...} //完成窗口初始化工作,完成窗口的注册,完成窗口的创建,显示和更新。 nReturnCode = pThread->Run(); //继承基类Run()方法,调用CWinThread::Run()来完成消息循环 ... } //////////////////////////////////////////////////////////////// CWinThread::Run()方法路径:MFC|SRC|THRDCORE.CPP int CWinThread::Run() { ... // phase2: pump messages while available do//消息循环 { // pump message, but quit on WM_QUIT if (!PumpMessage())//取消息并理 return ExitInstance(); ... } while (::PeekMessage(&m_msgCur, NULL, NULL, NULL, PM_NOREMOVE)); ... } 说明: BOOL PeekMessage(,,,,)函数说明 The PeekMessage function checks a thread message queue for a message and places the message (if any) in the specified structure. If a message is available, the return value is nonzero. If no messages are available, the return value is zero. ///////////////////////////////////////////////////////////// BOOL CWinThread::PumpMessage() { ... if (!::GetMessage(&m_msgCur, NULL, NULL, NULL))//取消息 {...} ... // process this message if (m_msgCur.message != WM_KICKIDLE && !PreTranslateMessage(&m_msgCur)) { ::TranslateMessage(&m_msgCur);//进行消息(如键盘消息)转换 ::DispatchMessage(&m_msgCur);//分派消息到窗口的回调函数理(实际上分派的消息经过消息映射,交由消息响应函数进行理。) } return TRUE; } 9,文档与视结构: 可以认为View类窗口是CMainFram类窗口的子窗口。 DOCument类是文档类。 DOC-VIEW结构将数据本身与它的显示分离开。 文档类:数据的存储,加载 视类:数据的显示,修改 10,文档类,视类,框架类的有机结合: 在CTEApp类CTEApp::InitInstance()函数通过文档模板将文档类,视类,框架类的有机组织一起。 ... CSingleDocTemplate* pDocTemplate; pDocTemplate = new CSingleDocTemplate( IDR_MAINFRAME, RUNTIME_CLASS(CTEDoc), RUNTIME_CLASS(CMainFrame), // main SDI frame window RUNTIME_CLASS(CTEView)); AddDocTemplate(pDocTemplate);//增加到模板
C++面向对象编程八皇后问题 BOOL CMyqueenApp::InitInstance() { AfxEnableControlContainer(); // Standard initialization // If you are not using these features and wish to reduce the size // of your final executable, you should remove from the following // the specific initialization routines you do not need. #ifdef _AFXDLL Enable3dControls(); // Call this when using MFC in a shared DLL #else Enable3dControlsStatic(); // Call this when linking to MFC statically #endif // Change the registry key under which our settings are stored. // TODO: You should modify this string to be something appropriate // such as the name of your company or organization. SetRegistryKey(_T("Local AppWizard-Generated Applications")); LoadStdProfileSettings(); // Load standard INI file options (including MRU) // Register the application's document templates. Document templates // serve as the connection between documents, frame windows and views. CSingleDocTemplate* pDocTemplate; pDocTemplate = new CSingleDocTemplate( IDR_MAINFRAME, RUNTIME_CLASS(CMyqueenDoc), RUNTIME_CLASS(CMainFrame), // main SDI frame window RUNTIME_CLASS(CMyqueenView)); AddDocTemplate(pDocTemplate); // Parse command line for standard shell commands, DDE, file open CCommandLineInfo cmdInfo; ParseCommandLine(cmdInfo); // Dispatch commands specified on the command line if (!ProcessShellCommand(cmdInfo)) return FALSE; VERIFY( 1 == InitSkinMagicLib( AfxGetInstanceHandle(), "Demo" , NULL, NULL ) ); VERIFY( 1 == LoadSkinFromResource( AfxGetInstanceHandle() , "DEFAULT" ,"DEFAULT") ); VERIFY( 1 == SetWindowSkin( m_pMainWnd->m_hWnd , "MainFrame" )); VERIFY( 1 == SetDialogSkin( "Dialog" ) ); //((CMainFrame*)m_pMainWnd)->m_bSkinned = TRUE; //((CMainFrame*)m_pMainWnd)->m_nIndex = 0; m_pMainWnd->SetWindowText("八皇后问题演示"); // The one and only window has been initialized, so show and update it. m_pMainWnd->ShowWindow(SW_SHOW); m_pMainWnd->UpdateWindow();
本资源含大量的图像理代码(C++) int kind = 0; // 图像类型(8位kind=1,24位kind=3,初始化kind=0) LONG Bytes = 0; // 图像分配内存的最大值 BOOL Step; // 菜单上一步、下一步启动禁用标志 -> FALSE为下一步禁用 BOOL Step_All = TRUE; // 初始化上一步、下一步 -> TRUE为禁用 BOOL fdj = TRUE; // 可以使用放大镜的标志 int screen_width = GetSystemMetrics(SM_CXSCREEN); // 获取屏幕宽度 int screen_height = GetSystemMetrics(SM_CYSCREEN); // 获取屏幕高度 BOOL DirectDraw_Pause = FALSE; // DirectDraw显示时键盘断标志 int Match_x = 0; // 模板匹配左上方坐标 - 行 int Match_y = 0; // 模板匹配左上方坐标 - 列 CString Match_result = ""; // 模板匹配结果 SOCKET m_socket; // 定义一个套接字 ///////////////////////////////////////////////////////////////////////////// // CMy002App initialization BOOL CMy002App::InitInstance() { // *** 判断程序是否已运行 *** HANDLE hMutex; // 定义一个句柄 // 创建一个互斥对象,并返回句柄 hMutex = CreateMutex(NULL, TRUE, "7 4 的程序"); // 主线程拥有互斥对象,相当于一次请求互斥对象 // hMutex = CreateMutex(NULL, FALSE, "7 4 的程序"); // 主线程不拥有互斥对象 // WaitForSingleObject(hMutex,INFINITE); // 请求互斥对象 if (hMutex) // 判断句柄是否有值 { if (ERROR_ALREADY_EXISTS == GetLastError()) // 判断程序是否已运行 { AfxMessageBox("该应用程序已运行! ", MB_ICONINFORMATION | MB_OK); ExitProcess(0); // 退出应用程序 } } ReleaseMutex(hMutex); // 释放互斥对象 // *** 登陆密码对话框 *** Password dlg; // 定义对话框对象 dlg.DoModal(); // 显示并运行模态对话框 - 用户登录对话框 // CG: The following block was added by the Splash Screen component. \ { \ CCommandLineInfo cmdInfo; \ ParseCommandLine(cmdInfo); \ \ C_SplashWnd::EnableSplashScreen(cmdInfo.m_bShowSplash); \ } AfxEnableControlContainer(); // Standard initialization // If you are not using these features and wish to reduce the size // of your final executable, you should remove from the following // the specific initialization routines you do not need. #ifdef _AFXDLL Enable3dControls(); // Call this when using MFC in a shared DLL #else Enable3dControlsStatic(); // Call this when linking to MFC statically #endif // Change the registry key under which our settings are stored. // TODO: You should modify this string to be something appropriate // such as the name of your company or organization. SetRegistryKey(_T("Local AppWizard-Generated Applications")); LoadStdProfileSettings(); // Load standard INI file options (including MRU) // Register the application's document templates. Document templates // serve as the connection between documents, frame windows and views. CMultiDocTemplate* pDocTemplate; pDocTemplate = new CMultiDocTemplate( IDR_MY002TYPE, RUNTIME_CLASS(CMy002Doc), RUNTIME_CLASS(CChildFrame), // custom MDI child frame RUNTIME_CLASS(CMy002View)); AddDocTemplate(pDocTemplate); // create main MDI Frame window CMainFrame* pMainFrame = new CMainFrame; if (!pMainFrame->LoadFrame(IDR_MAINFRAME)) return FALSE; m_pMainWnd = pMainFrame; // Parse command line for standard shell commands, DDE, file open CCommandLineInfo cmdInfo; ParseCommandLine(cmdInfo); // 启动时不打开子窗口 cmdInfo.m_nShellCommand = CCommandLineInfo::FileNothing; // Dispatch commands specified on the command line if (!ProcessShellCommand(cmdInfo)) return FALSE; // The main window has been initialized, so show and update it. pMainFrame->ShowWindow(m_nCmdShow); pMainFrame->UpdateWindow(); return TRUE; } ///////////////////////////////////////////////////////////////////////////// // CAboutDlg dialog used for App About class CAboutDlg : public CDialog // *** 关于对话框 *** { public: CAboutDlg(); // Dialog Data //{{AFX_DATA(CAboutDlg) enum { IDD = IDD_ABOUTBOX }; //}}AFX_DATA // ClassWizard generated virtual function overrides //{{AFX_VIRTUAL(CAboutDlg) protected: virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support //}}AFX_VIRTUAL // Implementation protected: //{{AFX_MSG(CAboutDlg) //}}AFX_MSG DECLARE_MESSAGE_MAP() }; CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD) { //{{AFX_DATA_INIT(CAboutDlg) //}}AFX_DATA_INIT } void CAboutDlg::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CAboutDlg) //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CAboutDlg, CDialog) //{{AFX_MSG_MAP(CAboutDlg) //}}AFX_MSG_MAP END_MESSAGE_MAP() // App command to run the dialog void CMy002App::OnAppAbout() { CAboutDlg aboutDlg; aboutDlg.DoModal(); } ///////////////////////////////////////////////////////////////////////////// // CMy002App message handlers BOOL CMy002App::PreTranslateMessage(MSG* pMsg) { // CG: The following lines were added by the Splash Screen component. if (C_SplashWnd::PreTranslateAppMessage(pMsg)) return TRUE; return CWinApp::PreTranslateMessage(pMsg); }

16,470

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC相关问题讨论
社区管理员
  • 基础类社区
  • Web++
  • encoderlee
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

        VC/MFC社区版块或许是CSDN最“古老”的版块了,记忆之中,与CSDN的年龄几乎差不多。随着时间的推移,MFC技术渐渐的偏离了开发主流,若干年之后的今天,当我们面对着微软的这个经典之笔,内心充满着敬意,那些曾经的记忆,可以说代表着二十年前曾经的辉煌……
        向经典致敬,或许是老一代程序员内心里面难以释怀的感受。互联网大行其道的今天,我们期待着MFC技术能够恢复其曾经的辉煌,或许这个期待会永远成为一种“梦想”,或许一切皆有可能……
        我们希望这个版块可以很好的适配Web时代,期待更好的互联网技术能够使得MFC技术框架得以重现活力,……

试试用AI创作助手写篇文章吧