八宝书库 > 文学其他电子书 > 深入浅出MFC第2版(PDF格式) >

第103部分

深入浅出MFC第2版(PDF格式)-第103部分

小说: 深入浅出MFC第2版(PDF格式) 字数: 每页4000字

按键盘上方向键 ← 或 → 可快速上下翻页,按键盘上的 Enter 键可回到本书目录页,按键盘上方向键 ↑ 可回到本页顶部!
————未阅读完?加入书签已便下次继续阅读!






                 之对象实体)的文件动作时,有许多幕后的、不易观察到的机制。让我们从使用者按下 



                 【Save As】菜单项目开始,追踪程序的进行。 



508 


…………………………………………………………Page 571……………………………………………………………

                                               第8章    Document…View  深入探討 



                               遍寻Scribble 程序,并没有发现曾经在哪里拦截过【Save As】 

                               命令消息,那么必是某个「CCmdTarget 衍生类别」曾经在其 

                               Message Map 中设定过对此消息之处理函数。我猜想 

                               CDocument 最有这个可能: 



                         BEGIN_MESSAGE_MAP(CDocument; CCmdTarget) 

                          BEGIN_MESSAGE_MAP(CDocument; CCmdTarget) 

                                 //{{AFX_MSG_MAP(CDocument) 

                                  //{{AFX_MSG_MAP(CDocument) 

                                 ON_MAND(ID_FILE_CLOSE; OnFileClose) 

                                  ON_MAND(ID_FILE_CLOSE; OnFileClose) 

                                 ON_MAND(ID_FILE_SAVE; OnFileSave) 

                                  ON_MAND(ID_FILE_SAVE; OnFileSave) 

                                 ON_MAND(ID_FILE_SAVE_AS; OnFileSaveAs) 

                                  ON_MAND(ID_FILE_SAVE_AS; OnFileSaveAs) 

                                 //}}AFX_MSG_MAP 

                                  //}}AFX_MSG_MAP 

                         END_MESSAGE_MAP() 

                          END_MESSAGE_MAP() 



         宾果!于是【Save As】引发CDocument::OnFileSaveAs 被调用。 



            void CDocument::OnFileSaveAs() 

             void CDocument::OnFileSaveAs() 

            { 

             { 

                if (!DoSave (NULL)) 

                 if (!DoSave (NULL)) 

                    TRACE0(〃Warning: File save…as failed。n〃); 

                     TRACE0(〃Warning: File save…as failed。n〃); 

            } 

             } 



BOOL CDocument::DoSave(LPCTSTR lpszPathName; BOOL bReplace) 

{ 

    CString newName = lpszPathName; 

    if (newName。IsEmpty()) 

    { 

        CDocTemplate* pTemplate = GetDocTemplate(); 

        newName = m_strPathName; 

        。。。 



        if (!AfxGetApp()…》DoPromptFileName (newName; 

          bReplace ? AFX_IDS_SAVEFILE : AFX_IDS_SAVEFILECOPY; 

          OFN_HIDEREADONLY | OFN_PATHMUSTEXIST; FALSE; pTemplate)) 

            return FALSE;    // don't even attempt to save 

    } 



    CWaitCursor wait; 



    if (!OnSaveDocument (newName)) 

    { 。。。 } 



                           下页 

    。。。 

} 



                                                                               509 


…………………………………………………………Page 572……………………………………………………………

                  第篇    深入  MFC  程式設計 



                   BOOL CDocument::OnSaveDocument(LPCTSTR lpszPathName) 

                   { 

                       CFileException fe; 

                       CFile* pFile = NULL; 

                       pFile = GetFile(lpszPathName; CFile::modeCreate | 

                               CFile::modeReadWrite | CFile::shareExclusive; &fe); 



                       CArchive saveArchive(pFile; CArchive::store | 

                                            CArchive::bNoFlushOnDelete); 

                       saveArchive。m_pDocument = this; 

                                                          虽然看起来像是调用CDocument::Serialize;但事实上 

                       saveArchive。m_bForceFlat = FALSE; 

                                                          因为Serialize是虚拟函数;而CScribbleDoc 已改写 

                       TRY 

                                                          它,而且目前的this指针是指向CScribbleDoc对象 

                       { 

                           CWaitCursor wait;              (别忘了整个追踪路线的起源是Scribble Docment 

                                                          我会在下一章消息绕行这一主题中解释更详尽一些), 

                           Serialize(saveArchive);  

                           saveArchive。Close();           所以这里调用的是CScribbleDoc::Serialize函数;哈 

                           ReleaseFile(pFile; FALSE);     ,这就是虚拟函数的妙用! 

                       } 

                       。。。 

                   }                          void CScribbleDoc::Serialize(CArchive& ar) 

                                               void CScribbleDoc::Serialize(CArchive& ar) 

                                               { 

                                                { 

                                                  。。。 

                                                   。。。 

                                                  m_strokeList。Serialize(ar); 

                                                   m_strokeList。Serialize(ar); 

                                               } 

                                                } 



                                                         m_strokeList 是个CObList对象  



                   void CObList::Serialize(CArchive& ar) 

                   { 

                       CObject::Serialize(ar); 

                       if (ar。IsStoring()) 

                                            本例之CObList 对象内有4个元素,所以输出资料0004 

                       { 

                           ar。WriteCount(m_nCount); 

                           for (CNode* pNode = m_pNodeHead; 

                                pNode != NULL; pNode = pNode…》pNext) 

                      for 

                           { 

                      loop                          CArchive 已针对

返回目录 上一页 下一页 回到顶部 0 0

你可能喜欢的