资源描述
单击此处编辑母版标题样式,单击此处编辑母版文本样式,第二级,第三级,第四级,第五级,#,1 Visual C+,的可视化集成开发环境,2 Windows,消息与命令,3,单文档与多文档程序,4,对话框与常用组件,5,通用对话框,大纲:,1,、,Visual C+,的可视化集成开发环境,教学目标,:,掌握,VC+IDE,,能够在该环境下熟练使用,AppWizard,生成应用程序框架。了解一个,C+,应用程序的主要组成以及运行特点,掌握一些必要的相关理论知识。,重点、难点,:,重点:熟悉,VC+IDE,,掌握,AppWizard,的使用方法,了解,C+,程序的主要组成。,难点:一些必要的理论知识:,MFC,库,,Win32API,等。,教学方法:,以演示为主,辅以实验教学。,教学内容:,集成开发环境,或者说是,IDE,,是一个集成了源代码编辑器、资源编辑器、程序编译器、程序调试工具等相关工具的集合体。整个环境的构建使得编辑应用程序源代码以及生成一个,Windows,应用程序等工作变得相对轻松。,IDE,提供了大量的实用工具来支持可视化编程。这些实用工具包括:项目工作区、,AppWizard,ClassWizard,,,WizardBar,等。,(一),项目工作区,项目工作区是,IDE,的一个最重要的组成部分。每一个应用程序都是由多个源文件组成的,另外还需要包含编译和,1.1,集成开发环境,调试时的参数文件和库文件名等,通常把这样一组完整的文件集合称作一个项目(或工程)。在一个项目工作区中可以处理:,(,1,)一个工程和它所包含的文件。,(,2,)一个工程的子工程。,(,3,)多个相互独立的工程。,(,4,)多个相互依赖的工程(可以是不同编程语言编写的)。,项目工作区一般位于屏幕的左侧,它包含下面三种视图:,(,1,)文件视图(,FileView,),显示所创建的工程。展开该文件夹可以查看工程中所包含的文件,一般包括:项目的源文件,头文件,资源文件等等。,(,2,)类视图,(ClassView),显示项目中定义的,C+,类。展开该文件夹显示当前工程中定义的所有类,展开类可查看类的数据成员和成员函数以及全局变量等。,利用,ClassView,可以方便快速地浏览应用程序所包含的类的定义或类中成员函数的定义。,(,3,)资源视图(,ResourceView,),显示当前活动项目中所包含的资源。包括对话框、菜单,快捷键等。,(二),AppWizard,(应用程序向导,),从本质上讲它是一个代码生成器,它创建一个带有特性(或者定制的)、含有类名及源代码文件名的,Windows,应用程序的基本框架。这些特性、类名都是通过对话框由用户指定的。,AppWizard,可以使你迅速开始一个应用程序,在以后的学习中我们要经常和它打交道。,(三),ClassWizard(,类向导),:,ClassWizard,使程序员从维护,Visual C+,类代码这样繁琐复杂的工作中解脱出来。在需要定义一个新类、一个新的虚函数、或者一个新的消息处理函数时,,ClassWizard,可以,编写函数原型、函数体以及进行,Windows,消息映射等。总之,ClassWizard,起到帮助程序员编写源代码、管理 源代码的作用。,(四)资源编辑器,单击,Visual C+Workspace,窗口的,Resource View,选项卡时,你可以选择一个资源,以进行编辑。这个主窗口中容纳了一个适合资源类型的资源编辑器。此窗口也可以容纳一个所见及所得的菜单编辑器和一个强大的对话框图形编辑器,并且,它还包含了编辑图标、位图和字符串的工具。在对话框编辑器中,除了标准的,Windows,控件和新的,Windows,常用控件之外,还允许你插入,ActiveX,控件。通常,每一个工程都有一个文本格式的资源脚本(,RC,)文件,它描述工程的菜单、对话框、字符串和快捷键资源。,RC,文件也可以有,#include,语句,以便从其他子目录中引进资源。这些资源包括特定的项目,例如位图(,BMP,)和图标(,ICO,)文件,以及所有,Visual C+,程序公有的资源。,1.2 Vc+,编程中的一些相关的概念,(一),MFC,库,MFC,是,Microsoft Foundation Class,的缩写。,MFC,库是微软公司开发出的功能强大的类库,用来供程序员开发,Windows,应用程序使用,换句话说,,MFC,库是可以在应用程序中使用的已经定义好的有关,C+,类的集合,根据约定,MFC,库类名以字母,C,作为开头。,MFC,库是我们学习的重点,我们所涉及到的是,6.0,版本的,MFC,库。根据约定,,MFC,库类名以字母,C,作为开头。,(二)应用程序框架,应用程序框架的一种定义是:提供一般应用程序需要的全部面向对象软件组件的集成集合。这个定义有点晦涩,通过一个具体的实例就很容易理解了。应用程序框架是类库的超集,一般的类库只是一种孤立的类的集合,用来嵌入到任何程序中,但是应用程序框架却定义了程序的结构。,(三),Win32API,早期的,Windows,程序员使用,C,语言编写,Win16API,的应用程序。今天,如果要编写,32,位应用程序,你必须直接或间接地使用新的,Win32 API,。大多数的,Win16,函数都有对应的,Win32,函数,但是参数会有变化。在,MFC,库中的许多类封装了,Win32,的,API,函数,因而在实际的,MFC,编程中,你可以使用全局的,Win32API,函数,也可以使用,MFC,库中类的成员函数。,(四)关于,ActiveX,控件,VB,自,1991,年面世以来一直非常流行,它成功的原因要归于其开放性,,VB,的,16,位版本支持,Visual Basic,控件(,VBX),,它是,VB,开发者可购买或者自己编写的随时可用的软件组件。在微软,MFC,开发小组也为,Microsoft Visual C+,程序员找到了在他们程序中使用,VBX,的方法。,VBX,是建立在,16,位段式结构的基础上的,不适于,32,位结构,现在,ActiveX,控件(以前称为,OLE,,或者,OCX,)以,Microsoft COM,(,Component Object Model),技术为基础,可以替代,VBX,。应用程序开发者可以在,VB,和,Visual C+6.0,中使用,ActiveX,,,ActiveX,是用,C+,编写的。我们可以不知道,ActiveX,的编写技术,我们只要学习在,Visual C+,应用程序中如何使用它们。,ActiveX,控件是软件模块,它插入到的,C+,程序中,与普通的,Windows,控件插入到程序中的方法一样,至少表面上是这样的。,(五),Windows,图形设备接口(,GDI,),许多,MS-DOS,程序直接写显存和打印机接口。这种技术的缺点是对每一种显示卡和每一种打印机型号,都需要提供驱动程序软件。,Windows,引入了一个名为图形设备接口,(,GDI,)的 抽象层。,Windows,提供视频和打印机驱动程序,所以,你的程序不必知道系统连接的显卡和打印机的类型。程序不是寻址硬件,而是调用,GDI,函数,这些函数引用名为设备环境(,DC,)的数据结构,Windows,把设备环境结构映射到物理设备,并发出适当的输入,/,输出指令。图形设备接口几乎与直接视频一样快,并且它允许不同的,Windows,应用程序来共享显示。,1.3 MFC,类库的框架结构,前面提到,,MFC,库是微软公司为了用户开发应用程序需要而开发出的功能强大的类库。,MFC,为程序员实现了所有应用程序的公共部分,它不仅包含了,C+,基类,还包含了,WinMain,函数(,Windows,下的主函数)以及其它一些支持菜单、窗口、对话框、设备上下文等的组件。,MFC,的核心是以,C+,形式封装了大部分的,Windows API,,因此,MFC,向用户提供了一个面向,Windows,中结构的简单的,C+,成员函数的接口。,MFC,类库可分为:基础类、宏和全局函数两个主要部分,(,1,)基础类。,MFC,中的基础类按功能可以分为一下几类:基类、应用程序框架类、命令相关类、文档,/,视图类、线程类、可视对象类、窗口类、对话框类、属性表类、控制类、菜单类、设备描述表类、绘图对象类、文件类、诊断类、异常类数据库类等等。,(,2,)宏和全局函数。,若某个函数或变量不是属于某一个具体的类,那么它就是一个全局函数或者是全局变量。宏和全局函数提供以下功能:数据类型、运行时刻对象类型服务、诊断服务、异常处理、,CString,格式化及信息框显示、消息映射、应用信息管理对象连接和嵌入(,OLE,)等。全局函数以“,Afx”,为前缀。所有全局变量都是以“,afx”,为前缀,宏不带任何前缀,但是全部是大写。,从继承关系来看,又可将,MFC,中的类分成两大类:大多数的,MFC,类是从,Cobject,继承下来的,,Cobject,类描述了几乎所有的,MFC,中其它类的一些公共特性。,Cobject,类为派生类提供的服务主要包括:对象诊断、输出对象内部信息、对象有效性检查、运行时访问类的信息、安全可靠地把通用的,Cobject,指针转化为派生类的指针,等等。另外一些类则不是从,Cobject,类继承下来的,这些类包括:字符串类(,CString,)、日期时间类(,CTime,)、矩形类(,CRect,)等。,下图是,MFC,库的框架图,1.4,对一个最简单的应用程序框架的分析,下面的代码是,MyApp,应用程序的头文件和实现文件。类,CMyApp,和,CMyFrame,都是从,MFC,库基类派生出来的:,/MyApp.h,/application class,class CMyApp:public CWinApp,public:,virtual BOOL InitInstance();,;,/frame window class,class CMyFrame:public CFrameWnd,public:CMyFrame();,protected:,/afx_msg indicates that the next two functions are part of the MFC library message dispatch system,afx_msg void OnLButtonDown(UINT nFlags,CPoint point);afx_msg void OnPaint();,DECLARE_MESSAGE_MAP(),;,下面是,MyApp,应用程序的实现文件:,#include/MFC library header file declares base classes,#include myapp.h,CMyApp theApp;/the one and only CMyApp object,BOOL CMyApp:InitInstance(),m_pMainWnd=new CMyFrame();,m_pMainWnd-ShowWindow(m_nCmdShow);,m_pMainWnd-UpdateWindow();,return TRUE;,BEGIN_MESSAGE_MAP(CMyFrame,CFrameWnd),ON_WM_LBUTTONDOWN(),ON_WM_PAINT(),END_MESSAGE_MAP(),CMyFrame:CMyFrame(),Create(NULL,MYAPP Application);,void CMyFrame:OnLButtonDown(UINT nFlags,CPoint point),TRACE(Entering CMyFrame:OnLButtonDown-%lx,%d,%dn,(long)nFlags,point.x,point.y);,/,在调试窗口显示,void CMyFrame:OnPaint(),CPaintDC dc(this);,dc.TextOut(0,0,“,Hello,world!,”,);/,在客户区输出,下面给出一些程序元素的分析,:,WinMain,函数:,Windows,要求应用程序有一个,WinMain,函数。在这个例子中,我们看不到,WinMain,函数,因为它被隐藏到应用程序框架内部了。,CMyApp,类:类,CMyApp,的一个对象代表一个应用程序。程序定义了一个全局的,CMyApp,对象,即,the App,。,CWinApp,基类决定,theApp,的大多数行为。,应用程序启动,:当用户启动应用程序时,,Windows,调用应用程序框架内置的,WinMain,函数,并且,,WinMain,寻找,CWinApp,派生出的全局构造的应用程序对象。不要忘记,在,C+,程序中,全局对象在主程序之前构造。,成员函数,CMyApp:InitInstance,:当,WinMain,函数找到应用程序对象时,它调用虚成员函数,InitInstance,,这个成员函数调用所需要的构造和显示应用程序的主框架窗口。,我们必须在派生的应用程序类中重载,InitInstance,,因为,CWinApp,基类不知道需要什么样的主框架窗口。,成员函数,CWinApp:run,函数,run,隐藏在基类中,但是它发送应用程序的消息到它的窗口,这样可以保持应用程序的运行。在,WinMain,调用,InitInstance,之后,便调用,run,。,CMyFrame,类:,类,CMyFrame,的一个对象代表应用程序的主框架窗口。当构造函数调用基类,CFrameWnd,的成员函数,Create,时,,Windows,创建实际窗口结构,应用程序框架把它连接到,C+,对象。函数,ShowWindow,和,UpdateWindow,也是基类的成员函数,必须调用他们来显示来显示窗口。,CMyFrame:OnLButtonDown,函数,:,鼠标左键按下映射到,CMyFrame,的一个成员函数。应用程序执行时,鼠标左键按下时,会调用这个函数,该函数调用,MFC,库的,TRACE,宏,以便在调试窗口显示信息。,CMyFrame:OnPaint,函数:,每次重新绘图时(在程序的开始,当用户改变窗口的大小,全部或部分窗口重新显现时),应用程序框架就调用,CMyFrame,的这个重要的映射成员函数。语句,Cpaint DC,与图形设备接口,(GDI),有关。,关闭应用程序:,用户通过主框架窗口来关闭应用程序。这个操作激发一系列事件的发生,包括,CMyFrame,对象的析构,从,Run,中退出、从,WinMain,中退出,CMyApp,对象的析构。,1.5,标识符命名方法,好的表示符命名方法使变量、函数易于记忆,并且程序的可都性大大提高。在,VC+,中对于变量、函数的命名有自己的一套方法,它是由微软的一个名叫西蒙尼的开发人员提出来的,由于西蒙尼的国籍是匈牙利,所以这种标识符命名法称作匈牙利命名法。,匈牙利命名法主要有两条规则:,(一)标识符的名字以一个或者多个小写字母开头,这些小写字母用来指定数据类型。下面是常见的数据类型的标准前缀:,前缀 数据类型,c,字符(,char,),s,短整型(,short,),n,整数(,integer,),sz,以,0,结尾的字符串,b,字节,i int,(整数),f BOOL,W,字(,WORD,无符号短整数),l,长整数(,long,),h HANDLE,(句柄,无符号,int,),m_,类的成员变量,fn,函数,dw,双字(,DWORD,无符号长整数),2 Windows,消息与命令,教学目标,:,了解,Windows,编程模式中的消息驱动机制,熟练使用,ClassWizard,进行变量定义,消息映射等。能够编写菜单并进行必要的命令消息映射,重点、难点,:,重点:使用,ClassWizard,进行消息映射,难点:消息的分类以及消息映射使用的模型。,教学方法:,以演示为主,辅以实验教学。,教学内容:,2.1,消息驱动机制,消息是一种报告有关事件发生的通知,类似于,DOS,下的用户输入。,Windows,应用程序是由消息驱动的。,Windows,操作系统允许多个任务同时运行,应用程序的输入输出由,Windows,统一管理;,Windows,系统下每一个窗口都维护一个消息队列,操作系统接收和管理所有输入消息、系统消息,并把它们发送给相应窗口的消息队列。应用程序初始化完成后,进入消息循环,维护自己的消息队列,从中取出消息,对其进行处理。编写消息处理函数是,Windows,编程的主要工作之一。,Windows,应用程序的消息来源有以下四种:,(1),输入消息:包括键盘和鼠标的输入。这一类消息首先放在系统消息队列中,然后由,Windows,将它们送入应用程序消息队列中,由应用程序来处理消息。,(2),控制消息:用来与,Windows,的控制对象,如列表框、按钮、检查框等进行双向通信。当用户在列表框中改动当前选择或改变了检查框的状态时发出此类消息。这类消息一般不经过应用程序消息队列,而是直接发送到控制对象上去。,(3),系统消息:对程序化的事件或系统时钟中断作出反应。一些系统消息,像,DDE,消息(动态数据交换消息)要通过,Windows,的系统消息队列,而有的则不通过系统消息队列而直接送入应用程序的消息队列,如创建窗口消息。,(4),用户消息:这是程序员自己定义并在应用程序中主动发出的,一般由应用程序的某一部分内部处理。,基于,MFC,类库的应用程序完成初始化后,调用,Run(),函数进入消息循环。在,CWnd,类(所有窗口类的基类)中预定义标准,Windows,消息的处理函数,处理函数的名称以“,On”,开始,用户可以根据需要重写这些函数。,在,CWnd,类中,标准,Windows,消息的处理函数声明都带有,afx_msg,关键字,例如消息,WM_PAINT,的处理函数被声明为:,afx_msg void OnPaint();,关键字,afx_msg,用于把消息处理函数与其它,CWnd,成员函数分开,这些函数是通过消息映射实现的,依赖于标准的预处理宏。预处理之后,关键字,afx_msg,的位置就变成了空白。以全局对象,theApp,为例,其中的消息映射如下:,BEGIN_MESSAGE_MAP(CEx01App,CWinApp),/AFX_MSG_MAP(CEx01App),ON_COMMAND(ID_APP_ABOUT,OnAppAbout),/,注意:,ClassWizard,(类向导)将可能添加或删除消息映射宏,/AFX_MSG_MAP,/,标准的基于文档的文件命令,ON_COMMAND(ID_FILE_NEW,CWinApp:OnFileNew),ON_COMMAND(ID_FILE_OPEN,CWinApp:OnFileOpen),/,标准的打印设置命令,ON_COMMAND(ID_FILE_PRINT_SETUP,CWinApp:OnFilePrintSetup),END_MESSAGE_MAP(),其中的,BEGIN_MESSAGE_MAP,和,END_MESSAGE_MAP,都是预处理宏,用于声明消息映射的开始和结束。而在类中重新修改的消息处理函数声明形式为:,/Generated message map functions,protected:,/AFX_MSG(CEx01Ciew),afx_msg void OnPaint();,/AFX_MSG,DECLARE_MESSAGE_MAP(),最后的,DECLARE_MESSAGE_MAP,宏,声明在该类中使用消息映射。,2.2,应用程序菜单,Windows,菜单是应用程序命令项列表,菜单项可以是文字或位图。通过选择菜单项使应用程序完成与菜单项相关的命令。,下面通过一个例子来介绍如何在应用程序中建立新菜单、如何在菜单中加入新的菜单项、如何为菜单项建立相应的命令处理函数以实现消息映射。,首先看看如何在已有的下拉菜单中增加一个菜单项。,第一步,编辑菜单项资源,步骤如下:,(1),运行,AppWizard,创建,Ex02,,选中“,Single document”,(单文档,SDI,)单选项后,直接按下,Finish,按钮。,(2),在项目工作区窗口中打开,ResourceView,(资源视图)。,(3),双击该视图中的,Menu,图标,展开菜单资源。,(4),双击,IDR_MAINFRAME,,打开菜单编辑器,如图,2.1,所示。,(5),可以看到,在“文件”菜单的最下方有一个空白菜单项,用户可以编辑这个菜单项来添加菜单项。也可以单击某个菜单项,然后按键盘上的,Insert,键,在选定的菜单项前面插入一个新的菜单项。,(6),双击空白菜单项,打开,Menu Item Properties,对话框,如图,2.2,所示。,图,2.1,菜单编辑器,图,2.2 Menu Item Properties,对话框,(7),在,Caption,文本框中输入新菜单项名,输入的名字是“,Demo”,。在,ID,组合框中输入新菜单项的,ID,。注意,这个,ID,必须是唯一的,不能和别的,ID,重名。一般菜单项,ID,的命令规则是:,ID_,菜单名,_,菜单项名。因此将该菜单项命名为,ID_FILE_DEMO,。,(8),关闭该对话框,新的菜单项已经添加到原有的菜单中。运行这个程序可以看到,在“文件”菜单的最下方有一个“,Demo”,菜单项,如图,2.3,所示。,注意:这里选,SDI,类型,一是为了简化程序设计,二是想让读者对比,SDI,应用程序(如本例的,Ex02,)和,MDI,应用程序在外观和使用上的一些区别,对,SDI,和,MDI,有一个简单了解。,第二步,进行消息映射。图,2.3,中,Demo,菜单项是灰色的,不可用,因为它没有命令处理函数。为此必须要对菜单项进行消息映射,为新的菜单项建立处理函数。操作步骤如下:,(,1,)在,View,菜单中选择,Class Wizard,选项或使用加速键,Ctrl+W,打开,ClassWizard,对话框,选中其中的,Message Maps,选项卡,如图,1.4,所示。,(,2,)在,Class Name,下拉列表框中选择,CEx02View,。,(,3,)在,Object IDs,列表框中选择菜单项,Demo,的,ID,,即,ID_FILE_DEMO,。,(,4,)在,Messages,列表框中单击,COMMAND,,此时,Add Function,按钮变亮,表示可以,图,23,添加了,Demo,菜单项的应用程序,图,2.4 ClassWizard,的,Message Maps,选项卡,添加处理函数。单击,Add Function,按钮或双击,COMMAND,,弹出,Add Member Function,对话框,如图,2.5,所示。,在,Member function name,编辑框中给出了系统推荐使用的函数名是,OnFileDemo,。通常可以使用这个缺省的名字,如果有特殊需要也可以修改它。单击,OK,按钮,这时可以在,Member functions,列表框中看到,Demo,菜单项的处理函数已经创建,如图,1.6,所示。也就是说,当用户选择,Demo,菜单项时,应用程序将调用,OnFileDemo,函数实现消息映射。,在图,2.6,中单击,OK,按钮完成消息映射。,图,2.5 Add Member Function,对话框,图,2.6,创建,Demo,的处理函数,OnFileDemo,第三步,编写响应程序代码。现在为,OnFileDemo,函数编写实际的处理程序。比如,当用户选择菜单项,Demo,时,在窗口中显示“您选择了,Demo,菜单项。”信息。操作步骤如下:,(1),在文档类,CEx02Doc,中声明一个,CString,对象,m_String,。从上一章可以知道,程序中的文档对象用于存储在视图中的数据,因此这里选择在文档类中创建字符串对象。,在项目,工作区,中选,ClassView,类视图,双击,CEx02Doc,,打开类编辑器,如图,2.7,所示。对,CEx02Doc.h,头文件中修改,CEx02Doc,类的定义:,class CEx02Doc:public CDocument,protected:/create from serialization only,CEx02Doc();,DECLARE_DYNCREATE(CEx02Doc),CString m_String;/,输入本行内容,程序中的黑体字部分表示需要输入的内容,本书下面章节的片段中均使用此方法。“,m_”,前缀声明成员变量是,Visual C+,的标准,读者应该习惯于使用这种变量声明方法。,(2),在,CEx02Doc,的构造函数中初始化,m_String,。在类视图中单击文档类,CEx02Doc,前面的“,+”,,将其展开。双击,CEx02Doc(),函数,将会在正文窗口内打开代码编辑器。对,CEx02Doc(),函数编辑如下:,CEx02Doc:CEx02Doc(),/TODO:add one-time construction code here,m_String=,;/,输入本行内容,(3),编辑,OnFileDemo(),函数,将,m_String,赋值为“您选择了,Demo,菜单项。”。在图,2.6,(若在屏幕上看不到它,按下,Ctrl+W,加速键)的,Member function,列表框中单击,OnFileDemo,然后按下,Edit Code,按钮或双击,OnFileDemo,出现,Ex02View.cpp,代码编辑窗口,并且光标已经处于需要编辑的函数,OnFileDemo,中。编辑,OnFileDemo(),函数:,void CEx02View:OnFileDemo(),/TODO:Add your command handler code here,CEx02Doc*pDoc=GetDocument();/,输入以下四行内容,ASSERT_VALID(pDoc);,pDoc-m_String=,您选择了,Demo,菜单项。,;,Invalidate();,由于对象,m_String,处于文档类,CEx02Doc,中,要在视图类中对这一对象进行存取,必须先获得一个指向文档对象的指针,这可通过,GetDocument,函数完成。,/ASSERT_VALID(),函数则用于确保一定能获取该指针,这是,Visual C+,的技术,如果不使用这一函数,可能会产生错误信息。,Invalidate(),函数使客户区内容失效,强迫程序调用,OnDraw(),函数,重新绘制视图。,(4),用,OnDraw,()函数重新绘制客户区。视图对象管理程序客户区,对客户区的绘制工作由成员函数,OnDraw(),完成。几乎所有应用程序的绘制工作都通过这一函数实现,编程时必须修改这个函数。,在项目工作区中单击类视图中,CEx02View,前面的“,+”,将其展开,双击,OnDraw(),函数,打开,CEx02View.cpp,编辑窗口,光标位于,OnDraw(),函数中。按下述内容对,OnDraw,函数进行编辑:,void CEx02View:OnDraw(CDC*pDC),CEx02Doc*pDoc=GetDocument();,ASSERT_VALID(pDoc);,/TODO:add draw code for native data here,pDC-TextOut(0,0,pDoc-m_String);/,输入本行,这里使用了,CDC,类的成员函数,TextOut(),函数,该函数用于在,CDC,设备类中显示字符串。它有三个参数,前两个参数用于指示字符串显示的相对位置,第三个参数用于传递要显示的字符串。,现在编译运行这个程序。在“文件”菜单中选择,Demo,菜单项,窗口中显示“您选择了,Demo,菜单项。”的信息,如图,2.8,所示。,建立新菜单的方法与添加菜单项类似,首先编辑菜单资源,然后为相应的菜单项建立消息映射,编写消息处理函数。在资源编辑器中建立新菜单的一般步骤如下:,图,2.8 Ex02,程序运行的结果,(1),打开菜单编辑器,可以看到在菜单的最右边有一个空白的菜单项,如图,2.9,所示。,(2),编辑该空白菜单项(双击它,出现对话框),将其命名为,NewMenu,,如图,2.10,所示。可以看到,,Pop-up,复选框是被选中的,表示本菜单带有弹出式子菜单,因此无须定义本菜单的,ID,。,(3),关闭,Menu Item Properties,对话框,,NewMenu,菜单下方已经自动增加了一个空白的菜单项,如图,2.11,所示。用户可以通过编辑该空白菜单项,向,NewMenu,菜单添加菜单项。,图,2.9,菜单编辑器,图,2.10 New Item Properties,对话框,图,2.11,为,NewMenu,添加菜单项,(4),向,NewMenu,菜单中添加两个菜单项,New1,和,New2,,并将其,ID,分别命名为,ID_NEWMENU_NEW1,和,ID_NEWMENU_NEW2,,如图,2.12,所示。,在,Windows,中常常可以看到,点击某个菜单项还可以显示下一级子菜单。例如为,NewMenu,的,New2,添加子菜单,Sub1,和,Sub2,的步骤如下:,(1),在菜单编辑器中双击,New2,菜单项,打开,Menu ItemProperties,对话框,如图,2.13,所示。,(2),选中对话框中的,Pop-up,复选框,此时,ID,下拉列表框中的,ID_NEWMENU_ NEW2,自动消失。关闭该对话框后,在菜单项,New2,右边出现一个黑色的三角和一个空的子菜单,如图,2.14,所示。,图,2.12,新菜单建立完成,图,2.13 Menu Item Properties,对话框,图,2.14 New2,带有下一级子菜单,(3),编辑,New2,的空白子菜单,添加,Sub1,和,Sub2,两个菜单项,如图,2.15,所示。并将它们的,ID,分别命名为,ID_NEWMENU_NEW2_SUB1,和,ID_NEWMENU_ NEW2_SUB2,。,无论菜单项在哪一级菜单中,建立它们的命令处理函数的方法都是一样的。因为所有的菜单项都有一个唯一的,ID,标识,菜单项所处的位置不影响它们的处理函数的编写。,图,2.15,为,NewMenu,添加子菜单,2.3,快捷键和加速键,1.,快捷键,“文件”菜单中的“,F”,带有下划线,这表示用户可以通过按下,Alt+F,打开“文件”菜单,而无须用鼠标选取。,F,称为“文件”菜单的快捷键。,增加快捷键非常简单,只要在给定菜单名或菜单项名中的某个位置多写一个“,&”,字符,就把该字符后面的那个字符定义成了快捷键。比如把,NewMenu,中的字母,Mp,定义为快捷键,只需将菜单名设置为,New&Menu,即可,如图,2.16,所示。,图,2.16,增加快捷键,2,加速键,加速键是用于某个菜单项的控制键,用户可以通过按这些键直接打开相应的菜单选项,而无须打开菜单选取。例如,在,Windows,中,按,Ctrl+V,与“编辑”菜单中的“粘贴”选择是相同的。,注意,只有菜单项才有加速键。,下面是向,NewMenu,菜单中的,New1,菜单项增加加速键,Ctrl+F1,的步骤:,(1),在项目工作区的资源视图中双击,Accelerator,图标。,(2),双击,IDR_MAINFRAME,图标,打开加速键编辑器,如图,2.17,所示。,(3),双击加速键编辑器中的最后一个空白项,打开,Accel Properties,对话框,如图,2.18,所示。,图,2.17,加速键编辑器,图,2.18 Accel Properties,对话框,(4),在,ID,下拉列表框中选择,New1,菜单项的,ID,,即“,ID_NEWMENU_NEW1”,。,(5),在,Key,下拉列表框中选择,VK_F1,,关闭对话框,把,Ctrl+F1,加入到,New1,菜单项中。,(6),最后还要将,New1,的标题改为“,New1 Ctrl+F1”,。,2.4,工具栏和状态栏,1,工具栏,工具栏显示一组按钮,每个按钮对应一个菜单项。工具栏按钮是方便直观的用户界面,用户可以直接点击某个按钮,其作用和选取相应菜单选项是相同的。,可以把任何菜单项连接到工具栏中的按钮。以“文件”菜单中的,Demo,菜单项为例,将其添加到工具栏的步骤如下:,(1),在项目工作区的资源视图中,双击,Toolbar,图标。,(2),双击,IDR_MAINFRAME,图标,打开工具栏编辑器,同时在它的右边出现一组工具栏绘图工具,如图,2.19,所示。,图,2.19,工具栏编辑器,(3),选取工具栏编辑器中工具栏最右边的空白按钮,使用绘图工具在新按钮中画出如图,2.19,所示的图形。,(4),双击工具栏编辑器中编辑好的新按钮,打开,Toolbar Button Properties,对话框,如图,2.20,所示。,(5),在,ID,下拉列表框中选择,ID_FILE_DEMO,,新的按钮已经连接到,Demo,菜单项上。运行程序,单击新按钮,可以看到窗口中显示出与选择,Demo,菜单项相同的信息,如图,2.21,所示。,2,状态栏,状态栏用于显示某些提示信息。当用户把鼠标移到某个菜单项或工具栏按钮上时,状态栏中通常会显示一些简单的信息,提示用户该选项可以做哪些操作。,图,2.20 Toolbar Properties,对话框,图,2.21,添加了工具栏按钮的应用程序,增加工具栏按钮的状态栏提示,只需在图,2.20,所示的,Toolbar Properties,对话框的,Prompt,文本框中放置相应信息即可。其操作步骤如下:,(1),打开需要增加提示的按钮的,Toolbar Properties,对话框。这里为,Demo,按钮增加提示信息,如图,2.22,所示。,(2),在,Prompt,文本框中输入这个按钮的说明,:“,在窗口显示相关的信息,n,演示信息”,这意味着当用户将鼠标移到,Demo,按钮上时,状态栏中将显示“在窗口显示相关信息”,而在鼠标旁边将显示“演示信息”。,再次运行程序,看一看当鼠标移到,Demo,按钮上时,是否会出现如图,2.23,所示的提示信息。,图,2.22,为工具栏按钮增加提示信息,图,2.23,添加了提示信息的工具栏按钮,3,单文档与多文档程序,教学目标,:,了解文档,/,视图的模式,掌握单文档和多文档主要区别。,能够开发简单的单文档应用程序,进一步强化应用前面所学的知识。,重点、难点,:,重点:文档对象与视图对象之间的关系。,难点:对文档,/,视图模式的理解。,教学方法:,以演示为主,辅以实验教学。,教学内容:,3.1,文档,视图结构,使用,MFC AppWizard,创建应用程序,首先要求用户确定应用程序的基本结构:单文档(,SDI,)、多文档(,MDI,)或基于对话框的应用程序界面。其中单文档或多文档创建的应用程序是基于文档的应用程序。,创建基于文档的应用程序一般需要经过以下几步:为每一种类型的文档定义一个派生自,CDocument,类的派生类;添加用于存储文档数据的成员变量;编写用于实现读取和修改文档数据的函数成员。,在,MFC,中,用文档,视图结构可将数据从用户对数据的观察中分离出来。文档用来管理应用程序的数据,视图用于显示文档并管理与用户的交互过程。实际上,视图在用户与文档之间起桥梁作用,如图,3.1,所示。,MFC AppWizard,创建的文档是从,CDocument,类派生的,视图类是从,CView,类派生的。,CDocument,类为应用程序定义的文档类提供基本功能,而,CView,类为应用程序定义的视图类提供基本功能。视图和文档连接在一起,在文档与用户间起中介作用。视图在屏幕上显示文档数据并把用户输入转换成对文档的
展开阅读全文