按键盘上方向键 ← 或 → 可快速上下翻页,按键盘上的 Enter 键可回到本书目录页,按键盘上方向键 ↑ 可回到本页顶部!
————未阅读完?加入书签已便下次继续阅读!
CNotSupportedException
CNotSupportedException
COleException
COleException
COleDispatchException
COleDispatchException
CResourceException
CResourceException
CUserException
CUserException
332
…………………………………………………………Page 395……………………………………………………………
第5章 總觀Application Framework
Windows API classes
这是MFC 声名最著的一群类别。如果你去看看源代码,就会看到这些类别的成员函数
所对应的各个Windows API 函数。
■ CWinThread 代表MFC 程序中的一个执行线程。自从3。0 版之后,所有的MFC
类别就都已经是thread…safe 了。SDK 程序中标准的消息循环已经被封装在此
一类别之中(你会在第6章看到我如何把这一部份开膛剖肚)。
■ CWinApp 代表你的整个MFC 应用程序。此类别衍生自CWinThread;要知
道,任何32 位Windows 程序至少由一个执行线程构成。CWinApp 内含有用
的成员变量如m_szExeName, 放置执行档档名, 以及有用的成员函数如
ProcessShellmand,处理命令列选项。
■ CWnd 所有窗口,不论是主框窗口、子框窗口、对话框、控制组件、view 视
窗,都有一个对应的C++ 类别,你可以想象「窗口handle 」和「C++ 对象」
结盟。这些C++ 类别统统衍生自CWnd,也就是说,凡衍生自CWnd 之类别才
能收到WM_ 窗口消息(WM_MAND 除外)。
所谓「窗口handle 」和「C++ 对象」结盟,实际上是CWnd 对象有一个成员变
数m_hWnd ,就放着对应的窗口handle 。所以,只要你手上有一个CWnd 对象
或CWnd 对象指针,就可以轻易获得其窗口handle:
HWND hWnd = pWnd…》m_hWnd;
■ CCmdTarget CWnd 的父类别。衍生自它, 类别才能够处理命令消息
WM_MAND。这个类别是消息映射以及命令消息绕行的大部份关键,我将
在第9章推敲这两大神秘技术。
■ GDI 类别、DC 类别、Menu 类别。
333
…………………………………………………………Page 396……………………………………………………………
第篇 湷觥 FC 程式設計
Application framework classes
这一部份最为人认知的便是Document/View ,这也是使MFC 跻身application framework
的关键。Document/View 的观念是希望把资料的本体,和资料的显像分开处理。由于文
件产生之际,必须动态生成Document/View/Frame 三种对象,所以又必须有所谓的
Document Template 管理之。
■ CDocTemplate、CSingleDocTemplate、CMultiDocTemplate Document Template 扮演
黏胶的角色,把Document 和View 和其Frame (外框窗口)胶黏在一块儿。
■ CSingleDocTemplate 一次只支持一种文件类型,CMultiDocTemplate 可同时支持多
种文件类型。注意,这和MDI 程序或SDI 程序无关,换句话说,MDI 程序
也可以使用CSingleDocTemplate,SDI 程序也可以使用CMultiDocTemplate 。
但是,逐渐地,MDI 这个字眼与它原来的意义有了一些出入(要知道,这个字眼早
在SDK 时代即有了)。因此,你可能会看到有些书籍这么说:MDI 程序使用
CMultiDocTemplate,SDI 程序使用CSingleDocTemplate 。
■ CDocument 当你为自己的程序由CDocument 衍生出一个子类别后,应该在其
中加上成员变量,以容纳文件资料;并加上成员函数,负责修改文件内容以及
读写档。读写文件由虚拟函数Serialize 负责。第8章的Scribble Step1 范例程序
有极佳的示范。
■ CView 此类别负责将文件内容呈现到显示装置上:也许是屏幕,也许是打印
机。文件内容的呈现由虚拟函数OnDraw 负责。由于这个类别实际上就是你在
屏幕上所看到的窗口(外再罩一个外框窗口),所以它也负责使用者输入的第
一线服务。例如第8章的Scribble Step1 范例,其View 类别便处理了鼠标的
按键动作。
High level abstractions
视觉性UI 对象属于此类,例如工具栏CToolBar、状态列CStatusBar、对话框列
CDialogBar。加强型的View 也属此类,如可卷动的ScrollView 、以对话框为基础的
334
…………………………………………………………Page 397……………………………………………………………
第5章 總觀Application Framework
CFormView、小型文字编辑器CEditView、树状结构的CTreeView,支持RTF 文件格式
的CRichEditView 等等。
Afx 全域函数
还记得吧,C++ 并不是纯种的对象导向语言(SmallTalk 和Java 才是)。所以,MFC
之中得以存在有不属于任何类别的全域函数,它们统统在函数名称开头冠以Afx 。
下面是几个常见的Afx 全域函数:
函数名称 说明
AfxWinInit 被WinMain (由MFC 提供)调用的一个函数,用做MFC GUI
程序初始化的一部份,请看第6章的「AfxWinInit AFX 内部
初始化动作」一节。如果你写一个MFC console 程序,就得
自行调用此函数(请参考Visual C++ 所附之Tear 范例程序)。
AfxBeginThread 开始一个新的执行线程(请看第14 章,# 756 页)。
AfxEndThread 结束一个旧的执行线程(请看第14 章,# 756 页)。
AfxFormatString1 类似printf 一般地将字符串格式化。
AfxFormatString2 类似printf 一般地将字符串格式化。
AfxMessageBox 类似Windows API 函数MessageBox 。
AfxOutputDebugString 将字符串输往除错装置(请参考附录D ,# 924 页)。
AfxGetApp 取得application object (CWinApp 衍生对象)的指针。
AfxGetMainWnd 取得程序主窗口的指针。
AfxGetInstance 取得程序的instance handle 。
AfxRegisterClass 以自定的WNDCLASS 注册窗口类别(如果MFC 提供的数个
窗口类别不能满足你的话)。
MFC 宏 (macros)
CObject 和CRuntimeClass 之中封装了数个所谓的object services ,包括「取得执行时期
的类别信息」(RTTI )、Serialization (文件读写)、动态产生对象。。。等等。所有衍生自CObject
335
…………………………………………………………Page 398……………………………………………………………
第篇 湷觥 FC 程式設計
的类别,都继承这些机能。我想你对这些名词及其代表的意义已经不再陌生…如果你没
有错过第3章的「MFC 六大技术仿真」的话。
■ 取得执行时期的类别信息(RTTI ),使你能够决定一个执行时期的对象的类别
信息,这样的能力在你需要对函数参数做一些额外的类型检验,或是当你要针
对对象属于某种类别而做特别的动作时,份外有用。
■ Serialization 是指将对象内容写到文件中,或从文件中读出。如此一来对象的
生命就可以在程序结束之后还延续下去,而在程序重新激活之后,再被读入。
这样的对象可说是〃persistent〃 (永续存在)。
■ 所谓动态的对象生成(Dynamic object creation ),使你得以在执行时期产生一
个特定的对象。例如document 、view 、和frame 对象就都必须支持动态对象
生成,因为framework 需要在执行时期产生它们(第8章有更详细的说明)。
此外,OLE 常常需要在执行时期做对象的动态生成动作。例如一个OLE server 程序必
须能够动态产生OLE items ,用以反应OLE client 的需求。
MFC 针对上述这些机能,准备了一些宏,让程序能够很方便地继承并