home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Tricks of the Windows Gam…ming Gurus (2nd Edition)
/
Disc2.iso
/
vc98
/
mfc
/
src
/
docmulti.cpp
< prev
next >
Wrap
C/C++ Source or Header
|
1998-06-16
|
6KB
|
236 lines
// This is a part of the Microsoft Foundation Classes C++ library.
// Copyright (C) 1992-1998 Microsoft Corporation
// All rights reserved.
//
// This source code is only intended as a supplement to the
// Microsoft Foundation Classes Reference and related
// electronic documentation provided with the library.
// See these sources for detailed information regarding the
// Microsoft Foundation Classes product.
#include "stdafx.h"
#ifdef AFX_CORE2_SEG
#pragma code_seg(AFX_CORE2_SEG)
#endif
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#define new DEBUG_NEW
/////////////////////////////////////////////////////////////////////////////
// CMultiDocTemplate construction/destruction
CMultiDocTemplate::CMultiDocTemplate(UINT nIDResource, CRuntimeClass* pDocClass,
CRuntimeClass* pFrameClass, CRuntimeClass* pViewClass)
: CDocTemplate(nIDResource, pDocClass, pFrameClass, pViewClass)
{
ASSERT(m_docList.IsEmpty());
m_hMenuShared = NULL;
m_hAccelTable = NULL;
m_nUntitledCount = 0; // start at 1
// load resources in constructor if not statically allocated
if (!CDocManager::bStaticInit)
LoadTemplate();
}
void CMultiDocTemplate::LoadTemplate()
{
CDocTemplate::LoadTemplate();
if (m_nIDResource != 0 && m_hMenuShared == NULL)
{
HINSTANCE hInst = AfxFindResourceHandle(
MAKEINTRESOURCE(m_nIDResource), RT_MENU);
m_hMenuShared = ::LoadMenu(hInst, MAKEINTRESOURCE(m_nIDResource));
m_hAccelTable =
::LoadAccelerators(hInst, MAKEINTRESOURCE(m_nIDResource));
}
#ifdef _DEBUG
// warnings about missing components (don't bother with accelerators)
if (m_hMenuShared == NULL)
TRACE1("Warning: no shared menu for document template #%d.\n",
m_nIDResource);
#endif //_DEBUG
}
CMultiDocTemplate::~CMultiDocTemplate()
{
#ifdef _DEBUG
if (!m_docList.IsEmpty())
TRACE1("Warning: destroying CMultiDocTemplate with %d documents alive.\n",
m_docList.GetCount());
#endif
// delete shared components
if (m_hMenuShared != NULL)
::DestroyMenu(m_hMenuShared);
if (m_hAccelTable != NULL)
::FreeResource((HGLOBAL)m_hAccelTable);
}
/////////////////////////////////////////////////////////////////////////////
// CMultiDocTemplate attributes
POSITION CMultiDocTemplate::GetFirstDocPosition() const
{
return m_docList.GetHeadPosition();
}
CDocument* CMultiDocTemplate::GetNextDoc(POSITION& rPos) const
{
return (CDocument*)m_docList.GetNext(rPos);
}
/////////////////////////////////////////////////////////////////////////////
// CMultiDocTemplate document management (a list of currently open documents)
void CMultiDocTemplate::AddDocument(CDocument* pDoc)
{
ASSERT_VALID(pDoc);
CDocTemplate::AddDocument(pDoc);
ASSERT(m_docList.Find(pDoc, NULL) == NULL); // must not be in list
m_docList.AddTail(pDoc);
}
void CMultiDocTemplate::RemoveDocument(CDocument* pDoc)
{
ASSERT_VALID(pDoc);
CDocTemplate::RemoveDocument(pDoc);
m_docList.RemoveAt(m_docList.Find(pDoc));
}
/////////////////////////////////////////////////////////////////////////////
// CMultiDocTemplate commands
CDocument* CMultiDocTemplate::OpenDocumentFile(LPCTSTR lpszPathName,
BOOL bMakeVisible)
{
CDocument* pDocument = CreateNewDocument();
if (pDocument == NULL)
{
TRACE0("CDocTemplate::CreateNewDocument returned NULL.\n");
AfxMessageBox(AFX_IDP_FAILED_TO_CREATE_DOC);
return NULL;
}
ASSERT_VALID(pDocument);
BOOL bAutoDelete = pDocument->m_bAutoDelete;
pDocument->m_bAutoDelete = FALSE; // don't destroy if something goes wrong
CFrameWnd* pFrame = CreateNewFrame(pDocument, NULL);
pDocument->m_bAutoDelete = bAutoDelete;
if (pFrame == NULL)
{
AfxMessageBox(AFX_IDP_FAILED_TO_CREATE_DOC);
delete pDocument; // explicit delete on error
return NULL;
}
ASSERT_VALID(pFrame);
if (lpszPathName == NULL)
{
// create a new document - with default document name
SetDefaultTitle(pDocument);
// avoid creating temporary compound file when starting up invisible
if (!bMakeVisible)
pDocument->m_bEmbedded = TRUE;
if (!pDocument->OnNewDocument())
{
// user has be alerted to what failed in OnNewDocument
TRACE0("CDocument::OnNewDocument returned FALSE.\n");
pFrame->DestroyWindow();
return NULL;
}
// it worked, now bump untitled count
m_nUntitledCount++;
}
else
{
// open an existing document
CWaitCursor wait;
if (!pDocument->OnOpenDocument(lpszPathName))
{
// user has be alerted to what failed in OnOpenDocument
TRACE0("CDocument::OnOpenDocument returned FALSE.\n");
pFrame->DestroyWindow();
return NULL;
}
pDocument->SetPathName(lpszPathName);
}
InitialUpdateFrame(pFrame, pDocument, bMakeVisible);
return pDocument;
}
void CMultiDocTemplate::SetDefaultTitle(CDocument* pDocument)
{
CString strDocName;
if (GetDocString(strDocName, CDocTemplate::docName) &&
!strDocName.IsEmpty())
{
TCHAR szNum[8];
wsprintf(szNum, _T("%d"), m_nUntitledCount+1);
strDocName += szNum;
}
else
{
// use generic 'untitled' - ignore untitled count
VERIFY(strDocName.LoadString(AFX_IDS_UNTITLED));
}
pDocument->SetTitle(strDocName);
}
/////////////////////////////////////////////////////////////////////////////
// CMultiDocTemplate diagnostics
#ifdef _DEBUG
void CMultiDocTemplate::Dump(CDumpContext& dc) const
{
CDocTemplate::Dump(dc);
dc << "m_hMenuShared = " << (UINT)m_hMenuShared;
dc << "\nm_hAccelTable = " << (UINT)m_hAccelTable;
dc << "\nm_nUntitledCount = " << m_nUntitledCount;
dc << "\nwith " << m_docList.GetCount() << " open documents";
POSITION pos = GetFirstDocPosition();
while (pos != NULL)
{
CDocument* pDoc = GetNextDoc(pos);
dc << "\nwith document " << (void*)pDoc;
}
dc << "\n";
}
void CMultiDocTemplate::AssertValid() const
{
CDocTemplate::AssertValid();
POSITION pos = GetFirstDocPosition();
while (pos != NULL)
{
CDocument* pDoc = GetNextDoc(pos);
ASSERT_VALID(pDoc);
}
}
#endif //_DEBUG
#ifdef AFX_INIT_SEG
#pragma code_seg(AFX_INIT_SEG)
#endif
IMPLEMENT_DYNAMIC(CMultiDocTemplate, CDocTemplate)
/////////////////////////////////////////////////////////////////////////////