版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、MFC微软基础类 vMFCMFC(Microsoft Foundation ClassMicrosoft Foundation Class)微软基础类微软基础类是是一个由一个由MicrosoftMicrosoft公司设计的类库。公司设计的类库。vMFCMFC框架定义了应用程序的轮廓,并提供了用户接口框架定义了应用程序的轮廓,并提供了用户接口的标准实现方法,程序员要做的就是通过接口把具体应的标准实现方法,程序员要做的就是通过接口把具体应用程序特有的东西填入这个轮廓。用程序特有的东西填入这个轮廓。vMFCMFC的目的是让应用程序员在应用程序框架的基础上的目的是让应用程序员在应用程序框架的基础上建立
2、建立WindowsWindows下的应用程序,这种方法相对于下的应用程序,这种方法相对于SDKSDK来说更来说更为简单。为简单。v采用采用MFCMFC方式编程提高了方式编程提高了WindowsWindows应用程序的开发效率。应用程序的开发效率。v认识认识MFCMFC只是一个过程、一个手段,最终目的是为了只是一个过程、一个手段,最终目的是为了良好并熟练地运用良好并熟练地运用MFCMFC。 采用MFC编程的优点使用标准化的程序代码结构,有利于程序员之间的交流。Visual C+为MFC提供了大量的工具支持,提高了编程效率。如利用MFC AppWizard创建MFC应用程序框架,利用ClassWi
3、zard方便地对Windows消息进行管理。MFC应用程序的效率较高,只比传统的Windows C程序低5%左右。并且,在MFC应用程序中还允许混合使用传统的Windows API函数。其它优势:完全支持Windows所有的函数、控件、消息、菜单及对话框;具有良好的稳定性和可移植性,更符合微软的风格等。 MFC体系结构MFC主要组成部分:类、宏和全局函数。类是MFC中最主要的内容。MFC类是以层次结构方式组织起来的。MFC中的类分成两部分,除了一些辅助类,大多数的MFC类是直接或间接从根类CObject派生而来。几乎每一个派生层次都与一具体的Windows实例相对应,如文档类、窗口类和视图类等
4、。MFC宏主要功能:消息映射、运行时对象类型服务、诊断服务、异常处理。 MFC约定:全局函数以“Afx”为前缀,全局变量以“afx”为前缀。 学习MFC的方法首先要对Windows编程概念和API函数有一定的了解,如Windows API有哪些功能和哪些常用的数据结构等。 学会抽象地把握问题,不求甚解,不要一开始学习Visual C+就试图了解整个MFC类库。从理解和使用两个方面学习MFC,理解MFC应用程序的框架结构。先大体上了解MFC的概念、组成和基本约定,从简单的类入手,结合程序设计,由浅入深,循序渐进、日积月累。 编程时如果MFC某个类能完成所需要的功能,可以直接调用已有类的方法(成员
5、函数)。否则,可以利用面向对象技术中的“继承”方法对MFC类的行为进行扩充和修改,从MFC中已有的类派生出自己需要的类。 学习MFC,另一点就是不要过分依赖于向导(Wizard)工具。向导能做许多工作,但同时掩饰了太多的细节。 MFC应用程序生成应用程序生成MFC中的常用类 CObject、CCmdTarget、CWinThread、CWinApp、CWnd、CFrameWnd、CDialog、CView、CStatic、CButton、CListBox、CComboBox、CEdit、CScrollBarMFC 中的大部分类都是从基类 CObject 中继承的,该类包含大部分 MFC 类所通
6、用的数据成员和成员函数;CWinApp 类是在建立应用程序时需要用到的,并且在任何程序中都只用一次;CWnd 类汇集了 Windows 中的所有通用特性、对话框和控制。CFrameWnd 类是从 CWnd 中继承的,并实现了标准的框架应用程序;CDialog 可分别处理无模式和有模式两种类型的对话框。CView 用于让用户通过窗口来访问文档。在MFC应用程序的CWinApp派生类对象theApp是一个全局变量,代表了应用程序运行的主线程。它在程序整个运行期间都存在,它的销毁意味着运行程序的消亡。MFC应用程序启动时,首先创建应用程序对象theApp,这时将自动调用应用程序类的构造函数初始化对象
7、theApp,然后由应用程序框架调用MFC提供的AfxWinMain()主函数。 AfxWinMain()主函数首先通过调用全局函数AfxGetApp()获取应用程序对象theApp的指针pApp,然后通过pApp调用应用程序对象的有关成员函数,完成程序的初始化和启动工作,最后调用成员函数Run(),进入消息循环。程序运行后将收到WM_PAINT消息,调用OnPaint()函数绘制客户区窗口。如果Run()收到WM_QUIT消息,则结束消息循环,然后调用函数ExitInstance(),结束程序运行。 MFC应用程序的生与死应用程序的生与死 hello程序流程 MFC应用程序对象之间的关系应用
8、程序对象之间的关系 MFC应用程序运行后各函数的调用关系应用程序运行后各函数的调用关系 InitInstance()函数是派生类唯一需要重函数是派生类唯一需要重载的函数,它负责应用程序的初始化。载的函数,它负责应用程序的初始化。CWinApp类CWinApp 类提供了用户与 Windows 应用程序之间进行交流的接口。在生成类的对象后,对象自动建立与 Windows 系统的连接、接收 Windows 传送的消息,并交给程序中相应的对象去处理,这就免去了程序员的许多工作,使得开发 C+的 Windows 程序变得简单方便。 CWinApp类的对象theApp将自动创建一个主线程,主线程中有一个循
9、环体,用来不断的从应用消息队列中提取消息,并发送回操作系统,让操作系统调用窗口过程函数,实现消息响应。CWinApp类通过消息映射宏的方式,方便开发人员完成消息与响应函数之间的对应关系,大大简化了编程难度与复杂度。CMainFrame类类 CMainFrame 是由 MFC 中的 CFrameWnd 派生的,所以它也是一个框架窗口。CMainFrame 是类 CXXView 的父类,即 CXXView 类的对象显示在主框架窗口的客户区中。在类 CMainFrame 中,系统已经从类 CFrameWnd 中继承了处理窗口的一般事件的 Windows消息,如改变窗口的大小、窗口最小化等的成员函数,
10、因此编程时程序员不必关心此类消息的处理,从而减轻了程序员的负担。当然,如果确实需要重新编写此类消息的成员函数,则需要对原有的成员函数进行重载。 当程序的一个实例被运行时,系统将根据前面在 CWinApp 类中介绍的文档模板对象自动生成类 CMainFrame、CXXView、CXXDoc 的对象,而不需要程序员主动地去创建这些类的对象。 类 CXXView 与 CXXDoc这两个类是密切相关的,文档是由文档模板对象生成的,并由应用程序对象管理,而用户则是通过与文档相联系的视窗对象来存储、管理应用程序中的数据,用户与文档之间的交互是通过与文档相关联的视窗对象进行的。生成一个新的文档时,MFC 程
11、序同时生成一个框架窗口,并且在框架窗口的客户区中生成一个视窗对象作为框架窗口的子窗口,这个子窗口以可视化的方式表现文档中的内容。视窗的重要功能就是负责处理用户的鼠标、键盘等操作,通过对视窗对象的处理达到处理文档对象的目的。MFC通用控件类和窗口类绘图类CClientDC 类:一般用来方便地创建和销毁一个设备环境。CClientDC 通常在堆栈上创建。析构函数自动调用ReleaseDC(),不会导致内存资源泄漏.CWindowDC 类:与 CClientDC 类相似,但它的工作范围是窗口的非客户区。 CPaintDC 类:仅允许绘制无效的窗口客户区而不是绘制整个窗口, CWnd:BeginPai
12、nt()与CWnd:EndPaint()配对使用;CMetaFileDC 类:用于创建元文件,元文件是一种磁盘文件,它包含了所有的绘图行为以及绘制图像所需要的绘图模式。常用的MFC文件和库文件 文文 件件 名名 称称说说 明明afxwin.h声明声明MFC核心类核心类afxext.hMFC扩展文件,声明工具栏、状态栏、拆分窗口等类扩展文件,声明工具栏、状态栏、拆分窗口等类afxdisp.h声明声明OLE类类afxdtctl.h声明支持声明支持IE 4公用控件的公用控件的MFC类,如类,如CImageList等等afxcmn.h声明声明Windows公共控件类公共控件类Mfc42.libMFCx
13、x.DLL的导入函数库(的导入函数库(Release版)版)Mfc42D.libMFCxx.DLL的导入函数库(的导入函数库(Debug版)版)MfcS42.libMFCSxx.DLL的导入函数库(的导入函数库(Static Release版)版)MfcS42D.libMFCSxxD.DLL的导入函数库(的导入函数库(Static Debug版)版)Mfc42U.libMFCxxU.DLL的导入函数库(的导入函数库(Unicode Release版)版)Mfc42UD.libMFCxxUD.DLL的导入函数库(的导入函数库(Unicode Debug版)版)MfcO42D.libMFCOxxD
14、.DLL的导入函数库(的导入函数库(OLE Debug版)版)MfcD42D.libMFCDxxD.DLL的导入函数库(的导入函数库(Database Debug版)版)Nafxcw.libMFC静态链接库(静态链接库(Release版)版)NafxcwD.libMFC静态链接库(静态链接库(Debug版)版)gdi32.libGDI32.DLL的导入函数库的导入函数库user32.libUSER32.DLL的导入函数库的导入函数库kernel32.libKERNEL32.DLL的导入函数库的导入函数库msvcrt.libMSVCRT.DLL(C运行函数库)的导入函数库运行函数库)的导入函数库
15、msvcrtd.libMSVCRTD.DLL(Debug版版C运行函数库)的导入函数库运行函数库)的导入函数库libcmt.libC运行函数静态链接库(多线程)运行函数静态链接库(多线程)libc.libC运行函数静态链接库(单线程)运行函数静态链接库(单线程)进入下一节进入下一节MFC消息管理 MFC应用程序消息处理的方式与SDK应用程序有所不同。MFC应用程序框架截取了Windows向应用程序发出的消息,再确定将消息发送给哪一个对象,可以根据需要利用函数重载对消息进行处理,但不需要处理的消息将由应用程序框架自动处理。消息管理包括消息的发送和处理。对于消息发送,MFC提供了类似于API函数功
16、能的消息发送函数,而MFC消息处理的内部机制则相对复杂一些。从编程的角度出发,我们只需了解其大致的原理。 MFC的消息分类 标 准标 准 W i n d o w s 消 息消 息 : 以: 以 W M _ 前 缀 ( 但 不 包 括前 缀 ( 但 不 包 括WM_COMMAND)开始的消息,包括鼠标消息、键盘消息开始的消息,包括鼠标消息、键盘消息和窗口消息,如和窗口消息,如WM_MOVE 、WM_PAINT等。等。 控件通知(控件通知(Control Notification)消息消息:对控件操作引起的消:对控件操作引起的消息,是控件和子窗口向其父窗口发出的息,是控件和子窗口向其父窗口发出的W
17、M_COMMAND通通知消息。例如,当用户修改了编辑控件中的文本后,编辑控知消息。例如,当用户修改了编辑控件中的文本后,编辑控件向其父窗口发送件向其父窗口发送WM_COMMAND通知消息通知消息。 命令(命令(Command)消息消息:由菜单项、工具栏按钮、快捷键等:由菜单项、工具栏按钮、快捷键等用户界面对象发出的用户界面对象发出的WM_COMMAND消息。命令消息与其消息。命令消息与其它消息不同,它可被更广泛的的对象如文档、文档模板、应它消息不同,它可被更广泛的的对象如文档、文档模板、应用程序对象、窗口和视图等处理。用程序对象、窗口和视图等处理。 自定义消息自定义消息MFC消息映射机制 MF
18、C采用消息映射(Message Map)机制取代C/C+语言中的switch-case结构来处理消息。MFC消息映射机制包括一组消息映射宏,一条消息映射宏把一个Windows消息和其消息处理函数联结起来。在类定义的结尾用DECLARE_MESSAGE_MAP()宏来声明使用消息映射。在 类 的 实 现 源 文 件 中 用 B E G I N _ M E S S A G E _ M A P ( ) 和END_MESSAGE_MAP()宏来定义消息映射。ON_COMMAND宏:消息映射宏的第一个参数为消息ID,第二个参数为消息处理函数。 如ON_COMMAND(ID_FILE_NEW,CWinAp
19、p:OnFile New)。MFC 使用ClassWizard帮助实现消息映射功能。v在 AppWizard产生的应用程序类的源码中,应用程序类的定义(头文件)包含了类似如下的代码: /AFX_MSG(CTttApp)afx_msg void OnAppAbout();/AFX_MSGDECLARE_MESSAGE_MAP()v应用程序类的实现文件中包含了类似如下的代码:BEGIN_MESSAGE_MAP(CTApp, CWinApp)/AFX_MSG_MAP(CTttApp)ON_COMMAND(ID_APP_ABOUT, OnAppAbout)/AFX_MSG_MAPEND_MESSAGE
20、_MAP()v头文件里是消息映射和消息处理函数的声明,实现文件里是消息映射的实现和消息处理函数的实现。它表示让应用程序对象处理命令消息 ID_APP_ABOUT,消息处理函数是OnAppAbout。 MFC应用程序MESSAGE_MAP消息映射形式BEGIN_MESSAGE_MAP(theclass, baseclass)/AFX_MSG_MAP(theclass)ON_ . . . . . . / MFC预定义的消息映射宏ON_MESSAGE(message , memberFxn) / 用户自定义的消息映射宏. . . . . . /AFX_MSG_MAPEND_MESSAGE_MAP()
21、注意:注意:特殊注解特殊注解“/“/AFX_MSG_MAP”AFX_MSG_MAP”是是ClassWizardClassWizard类向导类向导用于维护消息映射宏的标记,用户不要删除注解轻易修改注解用于维护消息映射宏的标记,用户不要删除注解轻易修改注解内的代码。内的代码。 例 利用ClassWizard为框架类添加消息WM_CLOSE、WM_DESTROY及菜单项“Edit|Copy”的消息处理函数,分析ClassWizard完成了哪些工作。 启动ClassWizard,添加要求的三个消息处理函数,ClassWizard将在类的实现文件中添加三个消息映射宏和消息处理函数。消息映射宏如下: BE
22、GIN_MESSAGE_MAP(CMainFrame, CFrameWnd) /AFX_MSG_MAP(CMainFrame) ON_WM_CREATE() / 由MFC AppWizard程序向导自动生成的消息映射 ON_WM_CLOSE() / 由ClassWizard类向导添加 ON_WM_DESTROY() ON_COMMAND(ID_EDIT_COPY, OnEditCopy) /AFX_MSG_MAP END_MESSAGE_MAP() ClassWizard在类的定义中声明了消息处理函数class CMainFrame : CFrameWndpublic: CMainFrame(
23、);protected: /AFX_MSG(CMainFrame) / 声明消息处理函数原形 a f x _ m s g i n t O n C r e a t e ( L P C R E A T E S T R U C T lpCreateStruct); / 由程序向导自动生成 afx_msg void OnClose(); / 由ClassWizard类向导添加 afx_msg void OnDestroy(); afx_msg void OnEditCopy(); /AFX_MSG DECLARE_MESSAGE_MAP() / 声明使用消息映射宏;消息的发送发送消息到一个窗口可以采用
24、传送(Send)或寄送(Post)方式,这两种方式之间的主要区别是消息被接收对象收到后是否立即被处理。Windows提供了三个API函数用于消息的发送。函数SendMessage()用于向一个或多个窗口传送消息,该函数将调用目标窗口的窗口函数,直到目标窗口处理完收到的消息,该函数才返回。 函数PostMessage()用于向一个或多个窗口寄送消息,它把消息放在指定窗口创建的线程的消息队列中,然后不等消息处理完就返回。函数SendDlgItemMessage()函数用于向对话框中指定的控件发送消息,直到目标控件处理完收到的消息,该函数才返回。 MFC将这三个函数封装为CWnd窗口类的成员函数,封
25、装了目标窗口句柄,它们将向调用它的窗口对象发送或寄送消息,如pMyView-SendMessage()的调用形式表示向pMyView所指对象发送消息。与用户输入相关的消息(如鼠标消息和键盘消息)通常是以寄送(Post)的方式发送,以便这些用户输入可以由运行较缓慢的系统进行缓冲处理。而其它消息通常是以传送(Send)的方式发送。手工处理消息映射创建自己的消息映射的具体过程:MFC允许用户自定义消息,常量WM_USER(为0 x0400)与第一个自定义消息值相对应,用户必须为自己的消息定义相对于WM_USER的偏移值。利用#define语句定义自己的消息,例如:#define WM_USER 0X
26、0400#define WM_USER1 WM_USER+0#define WM_USER2 WM_USER+1在BEGIN_MESSAGE_MAP()之后,END_MESSAGE_MAP()之前加入消息映射语句: ON_MESSAGE(message, memberFxn) 其中,message是消息名标识,memberFxn是对应的消息处理函数。必须在函数返回类型前面加上afx_msg标识,如: afx_msg LRESULT memberFxn (WPARAM wParam , LPARAM lParam);其中,参数wParam、lParam用于传递消息的两个附加信息。可 用CWnd:
27、SendMessage()函数或CWnd: PostMessage()函数发送消息。例 编写一个自定义消息应用程序,程序启动后设置一个定时器,在WM_TIMER的消息处理函数中发送一个用户自定义消息,在对应的自定义消息处理函数中以动画的形式旋转显示一行文本。 基本思路:基本思路: 用用WM_TIMERWM_TIMER消息处理函数发送消息;消息处理函数发送消息; 启动定时器启动定时器 销毁定时器销毁定时器 用自定义消息完成动画旋转显示功能。用自定义消息完成动画旋转显示功能。 自定义消息自定义消息IDID 定义消息映射定义消息映射1.1. 定义消息处理函数定义消息处理函数具体过程:1首先利用MFC
28、 AppWizardexe向导创建一个名为Rotate的应用程序。利用ClassWizard类向导为CRotateView类生成消息WM_CREATE的消息处理函数,通过设置定时器在指定的时间间隔向窗口发送WM_TIMER消息。 SetTimer(1,200,NULL); / 启动定时器2在文件RotateView.cpp开始位置定义一个用户自定义消息:#define WM_MYMESSAGE WM_USER+1 利用ClassWizard为CRotateView类生成消息WM_TIME的消息处理函数:SendMessage(WM_MYMESSAGE); 3在类CRotateView的定义中声
29、明自定义消息处理函数:afx_msg LRESULT OnMyMessage( WPARAM wParam, LPARAM lParam); 在文件RotateView.cpp消息映射BEGIN_MESSAGE_MAP 和END_MESSAGE_MAP之间添加自定义消息映射宏:ON_MESSAGE(WM_MYMESSAGE,OnMyMyessage) 4在类CRotateView的定义中声明一个private属性、int型的成员变量m_dEscapement,它表示文本显示角度,并在类CRotateView的构造函数中初始化:m_dEscapement=0;5利用ClassWizard生成消息
30、WM_DESTROY的消息处理函数,在销毁已创建的定时器:KillTimer(1); 6在文件RotateView.cpp中手工添加自定义消息处理函数实现代码,完成以动画形式旋转显示一行文本的功能。LRESULT CE6_6View:OnMyMessage(WPARAM wParam,LPARAM lParam) CClientDC dc(this); m_dEacapement=(m_dEacapement+100)%3600; CFont fontRotate; fontRotate.CreateFont(30,0,m_dEacapement,0,0,0,0,0,0,0,0,0,0,0);
31、 CFont *pOldFont=dc.SelectObject(&fontRotate); CRect rClient; GetClientRect(rClient); dc.FillSolidRect(&rClient,RGB(255,255,255); dc.TextOut(rClient.right/2,rClient.bottom/2,不登高山不知天之高也); dc.SelectObject(pOldFont); return 0;如果不考虑自定义消息,可以采用其他方式:如果不考虑自定义消息,可以采用其他方式: WM_TIMERWM_TIMER消息处理函数:消息处理函
32、数: 调用文本显示函数调用文本显示函数 旋转变量的计算旋转变量的计算 定义一个函数用来显示文本定义一个函数用来显示文本1.1. 定义一个变量用于文本的位置计算定义一个变量用于文本的位置计算进入下一节进入下一节第三章文档视图结构:MFC的三种窗体类型 在 MFC 中,文档是真正的数据载体,视图是文档的显示界面,对应于同一个文档,可能存在多个视图界面,需要另外一种东西将界面管理起来,即框架。 SDI单文档窗口:一次只处理一个文档,譬如记事本,绘图板;MDI多文档窗口:可同时处理多个文档,也意味着需要更多的额外编程工作。并不只是要跟踪所有打开的文档,还要提供 Window 菜单来管理特殊的程序特性;
33、Dialog对话框窗口:通常只需要显示少量的数据和获取少量的用户输入,除了节省资源外,对话框版本的应用程序的加载速度也更快些;文档和视图的四个核心类1.Cdocument(或COleDocument):该类负责存储和管理程序的数据,并为自定义的文档类提供基础的功能。一个文档代表一个数据单元,用户可以通过文件菜单上的“打开”命令打开文档,或通过文件菜单上的“保存”命令保存文档。2.Cview类或其派生类:该类为自定义的视图类提供了基础的功能。一个视图附加到一个文档并扮演一个文档和用户的中间人角色:视图显示文档的外观到屏幕上,并把用户的输入翻译成对文档的操作。此外,视图类还负责打印和打印预览的显示
34、。 CView 最常用的函数是 GetDocument,这个函数用于返回与此视图关联的文档。同时CView 具有窗口类的功能,可以方便的定义消息处理函数,MFC 定义了一个非常好的、在“文档-视图-框架”之间的消息传递机制。3.CFrameWnd类:该类支持一个文档的一个或多个视图的框架,框架窗口类定义了一个视图的容器。一个 SDI 程序只使用一个框架窗口CFrameWnd 类作为程序的顶层窗口提供视图的框架。一个 MDI 程序使用两种不同类型的框架窗口CMDIFrameWnd 作为顶层窗口,CMDIChildWnd 作为浮动窗口,为程序文档提供框架。4. CDocTemplate(CSing
35、leDocTemplate 或 CMultiDocTemplate):文档模板类支持某种类型的文档并管理这种类型的文档、视图和框架窗口对象。文档模板为了管理创建文档、视图和框架窗口的复杂过程,MFC 框架使用两种文档模板类:CSingleDocTemplate 类为 SDI(单文档)程序提供支持CMultiDocTemplate 类为 MDI(多文档)程序提供支持。一个 CSingleDocTemplate 类可以一次创建和存储一个类型的文档。文档对象由程序对象创建并维护,在程序的 InitInstance 方法中完成的一个关键任务是创建一个或多个适当类型的文档模板,程序对象为模板列表中的每个
36、文档模板存储一个指针,提供一个接口用来添加文档模板。如果需要支持两个或更多的文档类型,就应该为每种文档类型添加一个 AddDocTemplate 的调用。 多文档和多视图文档-视图程序不仅局限在一个文档和基于文档数据的视图,通过使用 MFC 的 Splitter窗口类,一个单文档接口(SDI)程序可以针对同一个文档实现两个或多个视图划分框架窗口客户区。文档-视图结构可以扩展到多文档接口(MDI)程序,以支持一个文档的多视图、多个打开的文档,甚至多个文档类型。 MDI 程序和 SDI 程序的主要不同1.MDI 程序从 CMDIFrameWnd 类继承顶层框架窗口,而不是 CFrameWnd 类。
37、 2.MDI 程序使用基于 CMDIChildWnd 类的子类来表示子框架窗口。 3.MDI 程序使用 CMultiDocTemplate 而不是 CSingleDocTemplate 来创建文档模板。4.在 CMultiDocTemplate 类中引用的框架窗口是子框架窗口类而不是顶层框架窗口。 5.MDI 程序有至少两个菜单资源,当没有文档打开时显示一个菜单,当有至少一个文档打开时显示另一个菜单。 单文档框架的初始化BOOL CSinglePadApp:InitInstance() / 使程序添加对 OLE 控件的包容支持 AfxEnableControlContainer(); #if
38、def _AFXDLL /当使用 MFC 动态库时,使程序控件具有 3D 外观 Enable3dControls(); #else /当使用 MFC 静态库时,使程序控件具有 3D 外观 Enable3dControlsStatic(); #endif / 程序用来存储配置信息的注册表值 SetRegistryKey(_T(Local AppWizard-Generated Applications); / 加载标准的 INI 文件选项(包括 MRU) LoadStdProfileSettings(); / 注册文档模板 CSingleDocTemplate* pDocTemplate; pD
39、ocTemplate = new CSingleDocTemplate( IDR_MAINFRAME, / 资源 ID,文档的名称 RUNTIME_CLASS(CSinglePadDoc), / 文档 RUNTIME_CLASS(CMainFrame), / 主要的 SDI 框架窗口 RUNTIME_CLASS(CSinglePadView); / 视图 / 把注册的文档模板添加到程序中 AddDocTemplate(pDocTemplate); / 解析命令行完成如标准 Shell 命令、DDE、文件打开操作 CCommandLineInfo cmdInfo; ParseCommandLin
40、e(cmdInfo); / 处理命令行中的命令 if (!ProcessShellCommand(cmdInfo) return FALSE; / 显示和更新窗口 m_pMainWnd-ShowWindow(SW_SHOW); m_pMainWnd-UpdateWindow(); return TRUE; 多文档框架的初始化BOOL CMultiPadApp:InitInstance() AfxEnableControlContainer(); / 使程序添加对 OLE 控件的包容支持 #if def _AFXDLL Enable3dControls(); / 使程序控件具有 3D 外观,当使
41、用 MFC 动态库时。 #else Enable3dControlsStatic(); / 使程序控件具有 3D 外观, #endif / 程序用来存储配置信息的注册表值 SetRegistryKey(_T(Local AppWizard-Generated Applications); LoadStdProfileSettings(); / 加载标准的 INI 文件选项(包括 MRU) / 注册文档模板 CMultiDocTemplate* pDocTemplate; pDocTemplate = new CMultiDocTemplate( IDR_MULTIPTYPE, / MDI 窗口
42、的资源 RUNTIME_CLASS(CMultiPadDoc), / MDI 文档 RUNTIME_CLASS(CChildFrame), / MDI 子框架 RUNTIME_CLASS(CMultiPadView); / MDI 视图 / 把注册的文档模板添加到程序中 AddDocTemplate(pDocTemplate); / 创建 MDI 主窗口 CMainFrame* pMainFrame = new CMainFrame; / 加载主窗口和主资源 if (!pMainFrame-LoadFrame(IDR_MAINFRAME) return FALSE; m_pMainWnd =
43、pMainFrame; / 解析命令行完成如标准 Shell 命令、DDE、文件打开操作 CCommandLineInfo cmdInfo; ParseCommandLine(cmdInfo); / 处理命令行中的命令 if (!ProcessShellCommand(cmdInfo) return FALSE; / 显示和更新窗口 m_pMainWnd-ShowWindow(SW_SHOW); m_pMainWnd-UpdateWindow(); return TRUE; 例子:生成一个多文档记事本视图选择为CEditView为基类不用写一行代码就实现了一个记事本,可以保存,打开文档文件不用
44、写一行代码就实现了一个记事本,可以保存,打开文档文件例子:实现多文档的MDI程序更更改改对对应应的的类类名名为为上上图图所所示示为了创建一个新的文档模板,为了创建一个新的文档模板,需要建立三个类,即需要建立三个类,即 CBallFrame(子框架窗口(子框架窗口类)、类)、CBallDoc(文档类)、(文档类)、CBallView(视图类)。(视图类)。添加添加IDR_MULTBTYPE菜单资源中菜单资源中NewHello,New Ball两个菜单项两个菜单项在在CMDIApp类中添加新增的两个菜单项的响应函数类中添加新增的两个菜单项的响应函数在在MultiBall.cpp文件中添加三个子类的
45、头文件,插入一个新的菜单资源文件中添加三个子类的头文件,插入一个新的菜单资源IDR_BALLTYPEBOOL CMDIApp:InitInstance()/ 加加Hello模板到模板列表模板到模板列表CMultiDocTemplate* pDocTemplate;pDocTemplate = new CMultiDocTemplate(IDR_MULTIBTYPE,RUNTIME_CLASS(CHelloDoc),RUNTIME_CLASS(CHelloFrame), / custom MDI child frameRUNTIME_CLASS(CHelloView);AddDocTemplat
46、e(pDocTemplate);/ 加球模板到模板列表加球模板到模板列表CMultiDocTemplate* pBallTemplate = new CMultiDocTemplate(IDR_BALLTYPE,RUNTIME_CLASS(CBallDoc),RUNTIME_CLASS(CBallFrame), / custom MDI child frameRUNTIME_CLASS(CBallView);AddDocTemplate(pBallTemplate);/ create main MDI Frame windowCMainFrame* pMainFrame = new CMain
47、Frame;if (!pMainFrame-LoadFrame(IDR_MAINFRAME)return FALSE;m_pMainWnd = pMainFrame;/ The main window has been initialized, so show and update it.pMainFrame-ShowWindow(m_nCmdShow);pMainFrame-UpdateWindow();return TRUE;添加新建文档的响应函数:添加新建文档的响应函数:OnNewHello,OnNewBall/ 下面两个菜单命令处理函数根据模板列表创建一个相应的新的视图文档下面两个菜单
48、命令处理函数根据模板列表创建一个相应的新的视图文档 void CMDIApp:OnNewHello()/ 搜索模板列表里包含搜索模板列表里包含Hello串的文档模式串的文档模式POSITION curTemplatePos = GetFirstDocTemplatePosition();while(curTemplatePos != NULL)CDocTemplate* curTemplate =GetNextDocTemplate(curTemplatePos);CString str;curTemplate-GetDocString(str, CDocTemplate:docName);i
49、f(str = _T(Hello)curTemplate-OpenDocumentFile(NULL);return;AfxMessageBox(No Hello Template);void CMDIApp:OnNewBall()/ 搜索模板列表里包含搜索模板列表里包含Ball串的文档模式串的文档模式POSITION curTemplatePos = GetFirstDocTemplatePosition();while(curTemplatePos != NULL)CDocTemplate* curTemplate =GetNextDocTemplate(curTemplatePos);C
50、String str;curTemplate-GetDocString(str, CDocTemplate:docName);if(str = _T(Ball)curTemplate-OpenDocumentFile(NULL);return;AfxMessageBox(No Ball Template);修改字符串资源中修改字符串资源中IDR_MULTIBTYPE的属性值的属性值插入新的字符串资源插入新的字符串资源IDR_BALLTYPE,并设置属性值,并设置属性值将CHelloView更改继承自CEditView类:替换CHelloView类源文件与头文件中所有的CView为CEditVi
51、ew;更改CHelloDoc类中Serialize序列化函数的实现为:(CEditView*)m_viewList.GetHead()-SerializeRaw(ar); 这样就可以实现将CHelloView由普通的视图类调整为可以编辑保存的编辑视图对象;在CBallView的OnDraw()函数中添加代码如下:CRect rect; GetClientRect(rect); pDC-SetTextAlign(TA_BASELINE | TA_CENTER); / 设置文本排列居中 pDC-SetTextColor(RGB(255,0,0); / 设置文本颜色 pDC-SetBkMode(TR
52、ANSPARENT); / 设置背景模式为透明 pDC-TextOut(rect.Width() / 2, rect.Height() / 2, Ball View, 9); 例子二 单文档多视图(分割视图)1.首先创建一个MFC单文档应用程序。2.添加4个MFC类TopLView、BottomLView、TopRView、BottomRView,基类为CView。3.添加一个MFC类CControlForm,基类为CFormView,对话框ID默认。4.创建一个切分类,如MySplitter,基类为CSplitterWnd(默认基类选项中无此类,可以先选择CFrameWnd类,生成后再修改为
53、CSplitterWnd类)。5.在框架类Cmainframe的头文件中,添加2个MySplitter的变量(因为下面要进行两次切分操作m_wndSplitter,m_wndSplitter2)。6.重写框架类CMainframe的OnCreateClient函数,如下:/第一次静态切分CreateStatic,一行两列if (!m_wndSplitter.CreateStatic(this,1,2) return FALSE;/第二次静态切分(将第一次切分后的第二列再分为2*2)及所有的子视图创建(CreateView函数)。if (!m_wndSplitter.CreateView(0,
54、0, RUNTIME_CLASS(CControlForm), CSize(100, 100), pContext) | !m_wndSplitter2.CreateStatic(&m_wndSplitter,2,2,WS_CHILD|WS_VISIBLE,m_wndSplitter.IdFromRowCol(0, 1)| !m_wndSplitter2.CreateView(0, 0, RUNTIME_CLASS(CTopLView), CSize(350, 240), pContext) | !m_wndSplitter2.CreateView(1, 0, RUNTIME_CLAS
55、S(CBottomLView), CSize(350, 240), pContext) | !m_wndSplitter2.CreateView(0, 1, RUNTIME_CLASS(CTopRView), CSize(350, 240), pContext) | !m_wndSplitter2.CreateView(1, 1, RUNTIME_CLASS(CBottomRView), CSize(350, 240), pContext) m_wndSplitter.DestroyWindow(); return FALSE;/ return CFrameWnd:OnCreateClient
56、(lpcs, pContext); /注释掉原有的响应函数注意:记得在Mainfrm.h中添加以上五个视图类的头文件:#include ControlForm.h#include TopLView.h#include TopRView.h#include BottomLView.h#include BottomRView.h#include “MySplitter.h”将CMySplitter的构造函数与析构函数改为public属性第四章:简单绘图绘制线条要求:单击鼠标左键并按住拖动后,释放鼠标左键,完成线条的绘图。1.新建单文档类型程序,名为Draw,添加鼠标左键按下及释放的消息响应函数;2
57、.为CDrawView类添加Cpoint类型成员变量m_ptOrigin;使用SDK全局函数绘制线条:GetDc可以在任意位置绘图,前提是得到任意绘图区域的句柄可以在任意位置绘图,前提是得到任意绘图区域的句柄必须记住释放资源必须记住释放资源利用MFC的CDC类绘图默认获得的是当前上下文环境下的设备句柄,默认获得的是当前上下文环境下的设备句柄,此处获得的是此处获得的是CDrawView对象的指针句柄对象的指针句柄利用MFC的CClientDC类绘图CClientDC类的构造函数会调用类的构造函数会调用GetDC,析,析构函数会调用构函数会调用ReleaseDC,因此不需要显式,因此不需要显式的释
58、放资源;的释放资源;当将当将this更改为更改为GetParent()函数时,则可以函数时,则可以在窗口的整个区域绘图包括菜单栏、工具栏,在窗口的整个区域绘图包括菜单栏、工具栏,非客户区域;因为非客户区域;因为CDrawView是由是由CMainFrame对象生成的,因此此处获得的对象生成的,因此此处获得的即为整个程序的框架窗口设备句柄;即为整个程序的框架窗口设备句柄;利用MFC的CWindowDC类绘图获得了桌面窗口的句柄,故可以实现在整个获得了桌面窗口的句柄,故可以实现在整个桌面绘图;桌面绘图;第五章:菜单操作GetMenu获得菜单项,获得菜单项,GetSubMenu获得菜单项的子获得菜单
59、项的子菜单,菜单,checkMenuItem设置设置/删除菜单项的复选标志删除菜单项的复选标志设置默认菜单项,将会以粗体方式显示加载图标菜单项获得默认的菜单项所能加载的位图的尺寸,并已消息获得默认的菜单项所能加载的位图的尺寸,并已消息框方式显示出来,此处为框方式显示出来,此处为13*13在位图资源编辑器中编辑位图,使之大小为在位图资源编辑器中编辑位图,使之大小为13*13,也可以采用其他工具调整位图大小;,也可以采用其他工具调整位图大小;移除和加载菜单项Cmenu为局部对象,可能导致异常,要么将为局部对象,可能导致异常,要么将menu对象更改为对象更改为CMainFrame的成员变量,的成员变
60、量,要么增加一条语句:要么增加一条语句:menu.Detach();创建快捷菜单(右键菜单)1.在资源选项的Menu文件夹下右键单击,选择Insert Menu 命名为 IDR_POPUP_MENU 在里面填一些菜单项;2.选中视图类,在属性中选择消息:WM_CONTEXTMENU,添加函数函数;void CMyDrawView:OnContextMenu(CWnd* pWnd, CPoint point)/ TODO: 在此处添加消息处理程序代码CMenu m_menu;m_menu.LoadMenuW(IDR_POPUP_MENU);CMenu *popupmenu = m_menu.GetSubMenu(0)
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 单位管理制度展示大全职工管理十篇
- Unit 1 语篇组合提升练
- 单位管理制度展示大合集员工管理篇
- 全球资产配置资金流向月报(2024年12月):强美元下12月资金流出非美市场流入美股
- 菲仔纸行业行业发展趋势及投资战略研究分析报告
- 2025小额贷款合同范本
- 2025基础装修工程合同
- 硬质合金刨刀片行业深度研究报告
- 经济技术开发区固废循环产业园项目可行性研究报告
- 2025年电线电缆用聚烯项目可行性研究报告
- 2024年酒店式公寓承包合同
- 2025年八省联考内蒙古高考生物试卷真题答案详解(精校打印)
- 校园公园绿化养护协议
- 猫抓病的护理
- 2024版城市绿化养护合同补充协议3篇
- 勘察设计工作内容
- GB/T 19799.2-2024无损检测超声检测试块第2部分:2号标准试块
- 2024-2025学年冀教新版八年级上册数学期末复习试卷(含详解)
- DB45T 1831-2018 汽车加油加气站防雷装置检测技术规范
- 《儿歌运用于幼儿园教育问题研究的文献综述》8600字
- 悬挂灯笼施工方案
评论
0/150
提交评论