MFC 多文档视图架构

目录

多文档视图架构

模仿多文档视图架构

执行流程


多文档视图架构

一个多文档视图架构运行后会是下面的样子:

内部的子框架窗口就相当于一个单文档视图架构,多文档视图架构就相当于在外面套一层框架窗口。

特点:可以管理多个文档(可以有多个文档类对象,即可以有多个数据)区别于单文档视图架构

模仿多文档视图架构

参与架构的类:CMDIFrameWnd(主框架窗口)、CMDIChildWnd(子框架窗口)、CWinApp(应用程序类)、CView(视图类)、CDocument(文档类)

需要用到的类:CDocTemplate(文档模板类)、CMultiDocTemplate(多文档模板类,文档模板类的子类)、CDocManager(文档管理类)

代码如下:

cpp 复制代码
#include <afxwin.h>
#include "resource.h"

class CMyDoc : public CDocument{
	DECLARE_DYNCREATE( CMyDoc )
};
IMPLEMENT_DYNCREATE( CMyDoc, CDocument )

class CMyView : public CView{
	DECLARE_DYNCREATE( CMyView )
public:
	virtual void OnDraw( CDC* pDC );
};
IMPLEMENT_DYNCREATE( CMyView, CView )

// 视图类必须重写OnDraw虚函数
void CMyView::OnDraw( CDC* pDC ){
	pDC->TextOut( 100, 100, "我是视图窗口" ); 
}
class CMyChild : public CMDIChildWnd{ 
	DECLARE_DYNCREATE( CMyChild )
};
IMPLEMENT_DYNCREATE( CMyChild, CMDIChildWnd )

// 继承主框架窗口类的类不能使用动态创建机制
class CMyFrameWnd : public CMDIFrameWnd{ //自己造主框架窗口类的对象
};

class CMyWinApp : public CWinApp{//自己造应用程序类的对象
public:
	virtual BOOL InitInstance( );
};
BOOL CMyWinApp::InitInstance( ){
	CMyFrameWnd* pFrame = new CMyFrameWnd;  // new一个主框架窗口类对象
	pFrame->LoadFrame( IDR_MENU1 );  // 给主框架窗口挂上菜单
	m_pMainWnd = pFrame;           // theApp->m_pMainWnd =  主框架窗口类对象
	pFrame->ShowWindow( SW_SHOW );
	pFrame->UpdateWindow( );

	// new一个多文档类对象
	CMultiDocTemplate* pTemplate = new CMultiDocTemplate( 
		IDR_MENU2,  // 给子框架窗口挂上菜单
		RUNTIME_CLASS(CMyDoc),
		RUNTIME_CLASS(CMyChild),
		RUNTIME_CLASS(CMyView)
	);

	// 
	AddDocTemplate( pTemplate );

	OnFileNew( );//创建文档类对象,创建子框架类对象,创建子框架窗口,创建视图类对象,创建视图窗口,文档类对象和视图类对象关联
	OnFileNew( );//创建文档类对象,创建子框架类对象,创建子框架窗口,创建视图类对象,创建视图窗口,文档类对象和视图类对象关联
	OnFileNew( );//创建文档类对象,创建子框架类对象,创建子框架窗口,创建视图类对象,创建视图窗口,文档类对象和视图类对象关联

	return TRUE;
}


CMyWinApp theApp;  //爆破点 

运行结果:

注意:需要给一个字符串资源,用于(父、子)框架窗口的标题命名

执行流程

在这里下断点,看看主框架窗口类对象的创建,this指针是pFrame主框架窗口类对象

调用函数LoadFrame(),this指针是pFrame主框架窗口类对象

调用Create函数创建

调用CreateEx函数,接下来就是之前分析的:

  • 给 CREATESTRUCT cs; 结构体成员赋值
  • 调用 PreCreateWindow(cs) :(1)注册窗口类(2)cs为空的成员重新赋值
  • AfxHookWindowCreate(this); (1)埋个钩子,类型是WHCBD (2)this是pFrame,保存到全局变量_AFX_THREAD_STATE中
  • 调用WIN API函数CreateWindowEx 创建主框架消息,消息会被钩子处理函数勾走。(1)pFrame对象与框架句柄绑定 (2)调用AfxWndProc函数

创建一个多文档模板类对象,触发构造函数,this指针是pTemplate

进入构造函数,接下来会调用父类的构造函数

赋值给多文档模板类对象的成员变量

m_doclist是多文档模板类对象pTemplate的成员变量,保存多个文档类对象地址

断言判断要求必须是空,之后的文档类对象会保存到这里

调用函数AddDocTemplate(),this指针是theApp

theApp对象的一个成员变量是m_pDocManager

调用函数AddDocTemplate(),this指针是m_pDocManager

把多文档模板类对象保存到m_templateList中

函数执行完毕,就形成下面的关系

调用函数 OnFileNew( );this指针是theApp

调用函数 OnFileNew( );this指针是theApp的成员m_pDocManager,文档管理类对象地址

取出多文档模板类对象地址,存储在pTemplate

调用函数OpenDocumentFile,函数内部this为多文档模板类对象地址

函数内部this为多文档模板类对象地址,调用函数CreateNewDocument();this指针是多文档模板类对象地址

动态创建文档类对象,并返回对象地址;

调用函数AddDocument()函数内部this为多文档模板类对象地址

将文档类对象扔到多文档模板类的链表成员中

调用CreateNewFrame函数内部this为多文档模板类对象地址

动态创建框子架类对象,并返回对象地址

创建子框架窗口

所以OnFileNew()函数,创建文档类对象,创建子框架类对象,创建子框架窗口,创建视图类对象,创建视图窗口,文档类对象和视图类对象关联

相关推荐
林开落L27 分钟前
前缀和算法习题篇(上)
c++·算法·leetcode
Prejudices40 分钟前
C++如何调用Python脚本
开发语言·c++·python
单音GG43 分钟前
推荐一个基于协程的C++(lua)游戏服务器
服务器·c++·游戏·lua
qing_0406031 小时前
C++——多态
开发语言·c++·多态
孙同学_1 小时前
【C++】—掌握STL vector 类:“Vector简介:动态数组的高效应用”
开发语言·c++
charlie1145141911 小时前
Qt Event事件系统小探2
c++·qt·拖放·事件系统
iiiiiankor1 小时前
C/C++内存管理 | new的机制 | 重载自己的operator new
java·c语言·c++
小辛学西嘎嘎1 小时前
C/C++精品项目之图床共享云存储(3):网络缓冲区类和main
c语言·开发语言·c++
c语言鹌鹑蛋2 小时前
C++初阶 --- 类和对象(1)
开发语言·c++
Jack黄从零学c++2 小时前
opencv(c++)图像的灰度转换
c++·人工智能·opencv