当前位置:网站首页>五、MFC视图窗口和文档
五、MFC视图窗口和文档
2022-07-27 00:18:00 【[T]】
一、视图窗口
提供一个用于显示数据的窗口
1、视图窗口相关类
CView及其子类,父类为CWnd类,封装了关于视图窗口的各种操作,以及和文档类的数据交互
2、视图窗口的使用
(1)定义了一个自己的视图类(CMyView),派生自CView,并重写父类成员纯虚函数void OnDraw(CDC* pDC),可以用于绘图
(2)其余框架类和应用类程序代码不变
(3)处理框架的WM_CREATE消息时,定义CMyView类对象,并调用Create函数创建视图窗口,视图窗口的ID为 AFX_IDW_PANE_FIRST
3、创建项目(MFCView)
(1)创建项目
(2)编写程序
#include <afxwin.h>
#include "resource.h"
class CMyView:public CView
{
DECLARE_MESSAGE_MAP()
public:
virtual void OnDraw(CDC* pDC);
afx_msg void OnPaint();
afx_msg void OnNew();
};
BEGIN_MESSAGE_MAP(CMyView, CView)
//ON_WM_PAINT()
ON_COMMAND(ID_NEW, OnNew)
END_MESSAGE_MAP()
//父类处理绘图消息时会调用OnDraw,当本类由绘图消息处理,则OnDraw不会被调用
void CMyView::OnDraw(CDC* pDC)
{
pDC->TextOut(100, 100, "CMyView::OnDraw");
}
void CMyView::OnPaint()
{
PAINTSTRUCT ps = {0};
HDC hdc = ::BeginPaint(m_hWnd, &ps);
::TextOutA(hdc, 200, 200, "CMyView::OnPaint", strlen("CMyView::OnPaint"));
::EndPaint(m_hWnd, &ps);
}
void CMyView::OnNew()
{
AfxMessageBox("视图类处理了OnNew消息");
}
class CMyFrameWnd:public CFrameWnd
{
DECLARE_MESSAGE_MAP()
public:
afx_msg void OnPaint();
afx_msg int OnCreate(LPCREATESTRUCT pcs);
afx_msg void OnNew();
};
BEGIN_MESSAGE_MAP(CMyFrameWnd, CFrameWnd)
ON_WM_CREATE()
ON_WM_PAINT()
ON_COMMAND(ID_NEW, OnNew)
END_MESSAGE_MAP()
int CMyFrameWnd::OnCreate(LPCREATESTRUCT pcs)
{
CMyView* pView = new CMyView;
pView->Create(NULL, "MFCView", WS_CHILD|WS_VISIBLE|WS_BORDER, CRect(0, 0, 200, 200),
this, AFX_IDW_PANE_FIRST); //AFX_IDW_PANE_FIRST 生成的视图窗口会平铺在框架窗口
m_pViewActive = pView; //将窗口赋值给活动窗口
return CFrameWnd::OnCreate(pcs);
}
void CMyFrameWnd::OnPaint()
{
PAINTSTRUCT ps = {0};
HDC hdc = ::BeginPaint(m_hWnd, &ps);
::TextOutA(hdc, 100, 100, "框架窗口客户区", strlen("框架窗口客户区"));
::EndPaint(m_hWnd, &ps);
}
void CMyFrameWnd::OnNew()
{
AfxMessageBox("框架类处理了OnNew消息");
}
class CMyWinApp:public CWinApp
{
DECLARE_MESSAGE_MAP()
public:
virtual BOOL InitInstance();
afx_msg void OnNew();
};
BEGIN_MESSAGE_MAP(CMyWinApp, CWinApp)
ON_COMMAND(ID_NEW, OnNew)
END_MESSAGE_MAP()
void CMyWinApp::OnNew()
{
AfxMessageBox("框架类处理了OnNew消息");
}
BOOL CMyWinApp::InitInstance()
{
CMyFrameWnd* pFrame = new CMyFrameWnd;
pFrame->Create(NULL, "MFCView", WS_OVERLAPPEDWINDOW, CFrameWnd::rectDefault,NULL,
(char*)IDR_MENU1);
m_pMainWnd = pFrame;
pFrame->ShowWindow(SW_SHOW);
pFrame->UpdateWindow();
return TRUE;
}
CMyWinApp theApp;(3)命令消息处理顺序
视图类 -》 框架类 -》 应用程序类
(4)对象关系图
theApp
theApp->m_pMainWnd = pFrame
pFrame->m_pViewActive = pView
二、文档类
相关类 CDocument,提供了用于管理数据的类,封装了关于数据的管理(数据提取,数据转换,数据存储等),并和视图类进行数据交互。
1、创建项目
(1)创建项目(MFCDoc)
(2)编写程序
#include <afxwin.h>
#include <afxext.h>
#include "resource.h"
class CMyDoc:public CDocument
{
};
class CMyView:public CView
{
DECLARE_DYNCREATE(CMyView)
DECLARE_MESSAGE_MAP()
public:
virtual void OnDraw(CDC* cDC);
afx_msg int OnCreate(LPCREATESTRUCT pcs);
};
IMPLEMENT_DYNCREATE(CMyView, CView)
BEGIN_MESSAGE_MAP(CMyView, CView)
ON_WM_CREATE()
END_MESSAGE_MAP()
void CMyView::OnDraw(CDC* cDC)
{
cDC->TextOut(100, 100, "视图窗口");
}
int CMyView::OnCreate(LPCREATESTRUCT pcs)
{
return CView::OnCreate(pcs);
}
class CMyFrameWnd:public CFrameWnd
{
DECLARE_MESSAGE_MAP()
afx_msg int OnCreate(LPCREATESTRUCT pcs);
afx_msg void OnPaint();
};
BEGIN_MESSAGE_MAP(CMyFrameWnd, CFrameWnd)
ON_WM_CREATE()
ON_WM_PAINT()
END_MESSAGE_MAP()
int CMyFrameWnd::OnCreate(LPCREATESTRUCT pcs)
{
return CFrameWnd::OnCreate(pcs);
}
void CMyFrameWnd::OnPaint()
{
PAINTSTRUCT ps = {0};
HDC hdc = ::BeginPaint(m_hWnd, &ps);
::TextOutA(hdc, 200, 200, "CMyFrameWnd::OnPaint", strlen("CMyFrameWnd::OnPaint"));
::EndPaint(m_hWnd, &ps);
}
class CMyWinApp:public CWinApp
{
public:
virtual BOOL InitInstance();
};
BOOL CMyWinApp::InitInstance()
{
CMyFrameWnd* pFrame = new CMyFrameWnd;
CCreateContext cct;
CMyDoc* pDoc = new CMyDoc;
cct.m_pNewViewClass = RUNTIME_CLASS(CMyView);
cct.m_pCurrentDoc = pDoc;
pFrame->LoadFrame(IDR_MENU1, WS_OVERLAPPEDWINDOW, NULL, &cct);
m_pMainWnd = pFrame;
pFrame->ShowWindow(SW_SHOW);
pFrame->UpdateWindow();
return TRUE;
}
CMyWinApp theApp;(3)创建过程
利用框架类对象地址(pFrame)调用LoadFrame函数,创建框架窗口
在处理框架窗口的WM_CREATE消息时,(父类CFrameWnd)动态创建视图类对象,并创建视图窗口
在处理视图窗口的WM_CREATE消息时,(父类CView)将文档类和视图类对象见理关系
2、创建流程
CMyFrameWnd* pFrame = new CMyFrameWnd;
CMyDoc* pDoc = new CMyDoc;
CCreateContext cct;
cct.m_pCurrentDoc = pDoc;//文档类对象地址
cct.m_pNewViewClass = RUNTIME_CLASS(CMyView);//&CMyView::classCMyView
pFrame->LoadFrame(... &cct)//函数内部this为pFrame
{
Create(...,&cct)//函数内部this为pFrame
{
CreateEx(...&cct)//函数内部this为pFrame
{
CREATESTRUCT cs;
....
cs.lpCreateParams = &cct;
::CreateWindowEx(...,&cct);//创建主框架窗口
}
}
}
//处理框架窗口的WM_CREATE消息
CFrameWnd::OnCreate( pcs )//函数内部this为pFrame,参数可以获取::CreateWindowEx的12个参数
{
CCreateContext* pContext = (CCreateContext*)pcs->lpCreateParams;//获取&cct
OnCreateHelper(pcs, pContext)//函数内部this为pFrame,pContext===&cct
{
OnCreateClient(pcs, pContext)//函数内部this为pFrame,pContext===&cct
{
CreateView(pContext..)//函数内部this为pFrame,pContext===&cct
{
CWnd* pView = pContext->m_pNewViewClass->CreateObject();
//动态创建视图类对象,并返回对象地址
pView->Create(..,pContext)//函数内部this为pView,pContext===&cct
{
CreateEx(..,pContext)//函数内部this为pView,pContext===&cct
{
CREATESTRUCT cs;
....
cs.lpCreateParams = pContext;//pContext===&cct
::CreateWindowEx(...,pContext);//创建视图窗口
}
}
}
}
}
}
//处理视图窗口的WM_CREATE消息
CView::OnCreate( pcs )//函数内部this为pView,参数可以获取::CreateWindowEx函数的12个参数
{
CCreateContext* pContext = (CCreateContext*)lpcs->lpCreateParams;//获取&cct
pContext->m_pCurrentDoc->AddView(pView)//函数内部this为pDoc,参数为视图类对象地址
{
m_viewList.AddTail(pView);//文档类对象用一个链表成员变量,保存视图类对象地址
pView->m_pDocument = this;//视图类对象用一个普通成员变量,保存文档类对象地址
}
}3、对象关系
(1)文档类对象用一个链表成员变量,保存视图类对象地址
(2)视图类对象用一个普通成员变量,保存文档类对象地址
一个文档类对象可以对应多个视图类对象(视图窗口)
一个视图类对象(视图窗口)只能对应一个文档类对象
4、视图切分
(1)相关类
CSplitterWnd 不规则框架窗口类,分装了关于不规则框架窗口的操作
(2)窗口切分的使用
重写CFrameWnd类的成员虚函数OnCreateClient
在虚函数中调用CSplitterWnd::CreateStatic创建不规则框架窗口
在虚函数中调用CSplitterWnd::CreateView创建视图窗口
(3)编写程序
#include <afxwin.h>
#include <afxext.h>
#include "resource.h"
class CMyDoc:public CDocument
{
};
class CMyView:public CView
{
DECLARE_DYNCREATE(CMyView)
DECLARE_MESSAGE_MAP()
public:
virtual void OnDraw(CDC* cDC);
afx_msg int OnCreate(LPCREATESTRUCT pcs);
};
IMPLEMENT_DYNCREATE(CMyView, CView)
BEGIN_MESSAGE_MAP(CMyView, CView)
ON_WM_CREATE()
END_MESSAGE_MAP()
void CMyView::OnDraw(CDC* cDC)
{
cDC->TextOut(100, 100, "视图窗口");
}
int CMyView::OnCreate(LPCREATESTRUCT pcs)
{
return CView::OnCreate(pcs);
}
class CMyFrameWnd:public CFrameWnd
{
DECLARE_MESSAGE_MAP()
afx_msg int OnCreate(LPCREATESTRUCT pcs);
afx_msg void OnPaint();
virtual BOOL OnCreateClient(LPCREATESTRUCT lpcs, CCreateContext* pContext);
private:
CSplitterWnd m_split; //不规则框架窗口
};
BEGIN_MESSAGE_MAP(CMyFrameWnd, CFrameWnd)
ON_WM_CREATE()
ON_WM_PAINT()
END_MESSAGE_MAP()
int CMyFrameWnd::OnCreate(LPCREATESTRUCT pcs)
{
return CFrameWnd::OnCreate(pcs);
}
void CMyFrameWnd::OnPaint()
{
PAINTSTRUCT ps = {0};
HDC hdc = ::BeginPaint(m_hWnd, &ps);
::TextOutA(hdc, 200, 200, "CMyFrameWnd::OnPaint", strlen("CMyFrameWnd::OnPaint"));
::EndPaint(m_hWnd, &ps);
}
BOOL CMyFrameWnd::OnCreateClient(LPCREATESTRUCT lpcs, CCreateContext* pContext)
{
//创建两个视图窗口
m_split.CreateStatic(this, 1, 2);
m_split.CreateView(0, 0, RUNTIME_CLASS(CMyView), CSize(100, 100), pContext);
m_split.CreateView(0, 1, pContext->m_pNewViewClass, CSize(100, 100), pContext);
return TRUE;
}
class CMyWinApp:public CWinApp
{
public:
virtual BOOL InitInstance();
};
BOOL CMyWinApp::InitInstance()
{
CMyFrameWnd* pFrame = new CMyFrameWnd;
CCreateContext cct;
CMyDoc* pDoc = new CMyDoc;
cct.m_pNewViewClass = RUNTIME_CLASS(CMyView);
cct.m_pCurrentDoc = pDoc;
pFrame->LoadFrame(IDR_MENU1, WS_OVERLAPPEDWINDOW, NULL, &cct);
m_pMainWnd = pFrame;
pFrame->ShowWindow(SW_SHOW);
pFrame->UpdateWindow();
return TRUE;
}
CMyWinApp theApp;
边栏推荐
- Debezium series: the binlog file cannot be recovered after the record is hung from the library server, and the task is switched to the main library to ensure that the data is not lost
- Interrupt, signal, system call
- Cloud development sleeping alarm clock wechat applet source code
- Use of formdata
- Getlocation:fail the API need to be declared in the requiredprivateinfo field in app.json
- 测试人需要的数据库知识:MySQL常用语法
- Ubuntu基于docker的mysql主从数据库配置
- BP plug-in temporary code record
- Kubeadmin到底做了什么?
- Favicon web page collection icon online production PHP website source code /ico image online generation / support multiple image format conversion
猜你喜欢
随机推荐
Manually build ABP framework from 0 -abp official complete solution and manually build simplified solution practice
Okaleido tiger is about to log in to binance NFT in the second round, which has aroused heated discussion in the community
Which securities firm is safer to open an account and buy REITs funds?
机器学习【Matplotlib】
关于url编解码应该选用的函数
Plato Farm通过LaaS协议Elephant Swap,为社区用户带来全新体验
Concept of data asset management
Knowledge points of test questions related to software testing
BP plug-in temporary code record
Debezium系列之:基于debezium offset拉取历史数据,确保数据没有丢失
If you want to thoroughly optimize the performance, you must first understand the underlying logic~
GoatGui邀你参加机器学习研讨班
Sort icons with swiper
小程序怎样助力智能家居生态新模式
Getlocation:fail the API need to be declared in the requiredprivateinfo field in app.json
C语言程序的编译(预处理)下
"Software testing" packaging resume directly improves the pass rate from these points
Rust web (I) -- self built TCP server
Web3.0 world knowledge system sharing - what is Web3.0
ZJCTF_login







![[Li Kou] 1859. Sort sentences](/img/0c/f7f698ad0052d07be98e5f888d7da9.png)

