在文檔里編程,,首先要搞清楚文檔/視圖架構(gòu)的運(yùn)行流程,如下: Document Document在MFC的CDocument里面被實(shí)例化. CDocument本身并無實(shí)際用途,它只提供一個(gè)空殼.當(dāng)我們開發(fā)自己的程序時(shí),應(yīng)該從CDocument派生一個(gè)屬于自己的Document類,并且在類中聲明一些成員變量,用以承載(容納)數(shù)據(jù).然后再(至少)改寫專門負(fù)責(zé)文件讀寫操作的Serialize函數(shù).事實(shí)上,AppWizard為我們把空殼都準(zhǔn)備好, 由于CDocument派生自CObject,,所以它就有CObject所支持的一切性質(zhì),,包括RTTI,Dynamic Creation,Serialization.又由于它也派生CCmdTarget,所以它可以接受來自菜單或工具欄的WM_COMMAND消息。 View View負(fù)責(zé)描述(呈現(xiàn))Document中的數(shù)據(jù),。 View在MFC的CView中被實(shí)例化,。CView只提供一個(gè)空殼,在開發(fā)過程中,,應(yīng)該從CView派生一個(gè)屬于自己的View類,,且在類中(至少)改寫專門負(fù)責(zé)顯示數(shù)據(jù)的OnDraw()函數(shù)(針對屏幕)或OnPaint()函數(shù)(針對打印機(jī))。其實(shí)AppWizard為我們把空殼都準(zhǔn)備好了,。 由于CView派生自CWnd,所以它可以接受一般的Windows消息(如WM_SIZE,WM_PAINT等等),,又由于它也派生自CCmdTarget,,因此它也可以接受菜單或工具欄的WM_COMMAND消息。 傳統(tǒng)C/SDK程序中,,當(dāng)窗口函數(shù)收到WM_APINT時(shí),,就調(diào)用BeginPaint,獲得一個(gè)Device Context(DC),然后在這個(gè)DC上作畫。這個(gè)DC代表屏幕裝置,。在MFC里面,,一旦WM_PAINT發(fā)生,Framework會(huì)自動(dòng)調(diào)用OnDraw函數(shù),。 View事實(shí)上是個(gè)沒有邊框的窗口,。真正出現(xiàn)時(shí),其外圍還有一個(gè)有邊框的窗口,,我們稱之為Frame窗口,。 Document Frame(View Frame) 若我們的程序管理兩種不同類型的數(shù)據(jù),比如說一個(gè)是TEXT,一個(gè)是BITMAP,作為程序設(shè)計(jì)者要為使用者多考慮一些:使用者可能在操作TEXT數(shù)據(jù)時(shí),,換一套TEXT專用的使用界面,,在使用者操作BITMAP數(shù)據(jù)時(shí),也換一套BITMAP界面,。這份工作是由Frame窗口負(fù)責(zé),。 為什么UI的管理不由View直接負(fù)責(zé),卻要交給Frame窗口,。將UI管理機(jī)能隔離出來,,可以降低彼此之間的依存性,也可以是機(jī)能重復(fù)使用于各種場合,,如SDI,MDI,OLE,In-Place editing(即地編輯)之中,。如此一來,View的彈性也會(huì)大一些,。 Document Template MFC把Document/View/Frame視為三位一體,。每當(dāng)使用者欲打開(或新增)一份文件,程序應(yīng)該做出Document,,View,,F(xiàn)rame各一份。這個(gè)“三口組”成為一個(gè)運(yùn)行單元,,由所謂的Document Template掌管,。MFC中有一個(gè)類CDocument負(fù)責(zé)此事。它又有兩個(gè)派生類,,分別CMultiDocTemplate 和CSingleDocTemplte. 若我們的程序能夠處理兩種數(shù)據(jù)類型,,必須制造兩個(gè)Document Template出來,并使用AddDocTemplate函數(shù)將它們一一加入系統(tǒng)之中。這和程序是不是MDI并無關(guān)系,。若程序支持多種數(shù)據(jù)類型,但卻是個(gè)SDI,,那只不過表示每次只能開啟一份文件,。 CDocTemplate是個(gè)抽象類,定義一些用來處理”Document/View/Frame三口組”的基礎(chǔ)函數(shù),。 CDocTemplate管理CDocument/CView/CFrameWnd Document Template管理“三口組“,,CWinAPP又來管理Document Template. File/New File/Open ↓ ↓ CWinApp選擇適當(dāng)?shù)腄ocument Template ↓CMyDoc 構(gòu)造Document對象 ↓ CCwndFrame CMyView 構(gòu)造Frame窗口對象 構(gòu)造View對象 ↓ ↗ ↓ 產(chǎn)生Frame窗口 <———— 產(chǎn)生View窗口 ↓ 讀文件(若是File/Open) ↓ 將View窗口初始化 ↓ 在View中顯示資料 注意:構(gòu)造View對象和產(chǎn)生View窗口的關(guān)系。View窗口就是地地道道的Windows窗口,,而為了對象管理,,MFC把View窗口外包一個(gè)專門的C++類別,那就是CView,。所以當(dāng)然是先構(gòu)造(Construct)一個(gè)View對象,,再由其構(gòu)造函數(shù)產(chǎn)生(Create)對應(yīng)的View窗口。 解釋CDocTemplate,CDocument,CView,CFrameWnd之間的關(guān)系: # CWinApp擁有一個(gè)對象指針:CDocManager *m_pDocManager # CDocManager擁有一個(gè)指針鏈表CPtrList m_templateList,,用來維護(hù)一系列的Document Template.一個(gè)程序若支持兩種文件類型,,就應(yīng)該有兩份Document Templates,應(yīng)用程序應(yīng)該在CMyViewApp::InitInstance中以AddDocTemplate將這些Document Templates加入到由CDocManager所維護(hù)的鏈表中,。 # CDocTemplate擁有三個(gè)成員變量,,分別持有Document,View,Frame的CRuntimeClass指針,另有一個(gè)成員變量m_nIDResource,用來表示此Document顯示時(shí)應(yīng)該采用的UI對象,。這四份數(shù)據(jù)應(yīng)該在CMyWinApp::InitInstance函數(shù)構(gòu)造CDocTemplate時(shí)指定,,成為構(gòu)造函數(shù)的參數(shù)。 # CDocument有一個(gè)成員變量CDocTemplate * m_pDocTemplate,,回指Document Template,;另有一個(gè)成員變量CPtrList m_viewList,表示它可以同時(shí)維護(hù)一系列的Views。 # CFrameWnd有一個(gè)成員變量CView * m_pViewActive,指向當(dāng)前活動(dòng)的View. # CView有一個(gè)成員變量CDocumnet *m_pDocumnt,指向相關(guān)的Document.
|
|