To enumerate all open documents in MDI (Multiple Document Interface) MFC applications we can do the following:
- Use CWinApp::GetFirstDocTemplatePosition and CWinApp::GetNextDocTemplate to get application document templates.
- For each document template, use CDocTemplate::GetFirstDocPosition and CDocTemplate::GetNextDoc to get contained documents.
Getting documents list
// MyMDIApp.h // ... typedef CTypedPtrList<CObList, CDocument*> DocsPtrList; // ... class CMyMDIApp : public CWinApp { // ... public: void GetAllDocuments(DocsPtrList& listDocs); // ... };
// MyMDIApp.cpp // ... void CMyMDIApp::GetAllDocuments(DocsPtrList& listDocs) { // clear the list listDocs.RemoveAll(); // loop through application's document templates POSITION posDocTemplate = GetFirstDocTemplatePosition(); while(NULL != posDocTemplate) { CDocTemplate* pDocTemplate = GetNextDocTemplate(posDocTemplate); // get each document open in given document template POSITION posDoc = pDocTemplate->GetFirstDocPosition(); while(NULL != posDoc) { CDocument* pDoc = pDocTemplate->GetNextDoc(posDoc); listDocs.AddTail(pDoc); // add document to list } } }
Example using documents list
This example calls CMyMDIApp::GetAllDocuments to get a list of all open documents, then fill a combobox control with document titles.
Also, it keeps the document pointers in each item data for further use (e.g. the application can activate the selected document at user request).
// MoreWindowsDlg.h //... class CMoreWindowsDlg : public CDialog { // ... public: virtual BOOL OnInitDialog(); private: CListBox m_listDocs; void _FillDocumentsListBox(); protected: afx_msg void OnBnClickedButtonActivate(); };
// MoreWindowsDlg.cpp // ... BOOL CMoreWindowsDlg::OnInitDialog() { CDialog::OnInitDialog(); _FillDocumentsListBox(); //... return TRUE; } void CMoreWindowsDlg::_FillDocumentsListBox() { // reset documents listbox control m_listDocs.ResetContent(); CMyMDIApp* pApp = (CMyMDIApp*)AfxGetApp(); ASSERT_VALID(pApp); // get a list of all open documents DocsPtrList listDocs; pApp->GetAllDocuments(listDocs); POSITION pos = listDocs.GetHeadPosition(); while(NULL != pos) { CDocument* pDoc = listDocs.GetNext(pos); // add document title to listbox control const CString strTitle = pDoc->GetTitle(); int nPos = m_listDocs.AddString(strTitle); // keep in mind the document pointer for further use m_listDocs.SetItemData(nPos, (DWORD_PTR)pDoc); } } void CMoreWindowsDlg::OnBnClickedButtonActivate() { const int nCurSel = m_listDocs.GetCurSel(); if(LB_ERR != nCurSel) { // activate the selected document CDocument* pDoc = (CDocument*)m_listDocs.GetItemData(nCurSel); ASSERT_KINDOF(CDocument, pDoc); POSITION pos = pDoc->GetFirstViewPosition(); if(NULL != pos) { CView* pView = pDoc->GetNextView(pos); CFrameWnd* pFrame = pView->GetParentFrame(); pFrame->ActivateFrame(); } } }
Resources
- MSDN: CWinApp::GetNextDocTemplate
- MSDN: CDocTemplate::GetNextDoc
See also
- Romanian version: Cum enumar documentele intr-o aplicatie MDI?