MDI文档模板类:
在 InitInstance 函数中,MDI模板是通过类似以下的形式来构造,与SDI不同:
CMultiDocTemplate* pDocTemplate;
pDocTemplate = new CMultiDocTemplate (
IDR_XXXTYPE,
RUNTIME_CLASS(CXXXDoc),
RUNTIME_CLASS(CChildFrame), // custom MDI chile frame
RUNTIME_CLASS(CXXXView) );
AddDocTemplate( pDocTemplate );
AddDocTemplate的调用使得MDI应用程序能够支持多个子窗口,而每个子窗口都与一个文档对象和一个视图对象相连接。若干个子窗口(及其相应的视图对象)也可能与同一个文档对象相连。
当应用程序在运行时,文档模板对象记录了所有从该模板创建的活动文档对象的一个列表。CMultiDocTemplate 的成员函数 GetFirstDocPosition() 和 GetNextDoc() 允许在该列表中作迭代操作。用 CDocument::GetDocTemplate 可以从文档转到相应的模板上来。
MDI框架窗口和MDI子窗口:
SDI只能有一个框架窗口和一个框架窗口对象。MDI应用程序有两个框架窗口类,并且可以有多个框架对象。如下:
基 类 | AppWizard产生的类 | 对象数目 | 菜单 | 视图 | 对象的创建
CMDIFrameWnd CMainFrame OnlyOne Yes No 在InitInstance() 中
CMDIChildWnd CChildFrame 每个子窗口有一个 No Yes 新子窗口被打开时
在SDI应用程序中,CMainFrame 对象不但构成了应用程序的框架,还包含了视图对象;而在MDI应用程序中,这两部分是分开完成的。CMainFrame 对象是在 InitInstance 函数中被创建,而视图则包含在CChildFrame 对象中。AppWizard 产生的代码:
CMainFrame* pMainFrame= new CMainFrame ;
if ( !pMainFrame->LoadFrame ( IDR_MAINFRAME ) )
return FALSE;
m_pMainWnd = pMainFrame;
(代码调用ProcessShellCommand以创建子窗口)
pMainFrame-> ShowWindow(m_nCmdShow);
pMainFrame-> UpdateWindow() ;
应用程序框架可以动态地创建 CChildFrame 对象,因为 CChildFrame 已经被传给 CMultiDocTemplate类的构造函数。
MDI的InitInstance () 将 CWinApp 类的数据成员 m_pMainWnd 设置成了指向应用程序的主框架窗口的指针。任何时候想得到应用程序的主框架窗口,都可以调用全局函数 AfxGetApp()->m_pMainWnd 来访问。