Click here to Skip to main content
Click here to Skip to main content

How to find a doctemplate object given its resource identifier

, 29 Oct 2003
Rate this:
Please Sign up or sign in to vote.
A useful function to find the doctemplate object by its numeric resource identifier in a MFC application.

Introduction

I have developed some very large applications, with tens of different doctemplate objects. Sometimes in my applications one view must respond to the user selection by opening another document of a different template. Thanks to the CWinApp member functions, we can search among all doctemplates and their open documents but how can we recognize a particular doctemplate?

We could check a string against the string returned by the GetDocString member function of CDocTemplate, but strings may change during the development of the application. The CDocTemplate class has a member variable named m_nIDResource which contains the numeric resource identifier passed to the constructor when the doctemplate object is created. This identifier is used for loading the doctemplate string from the resource, but also for the default menu associated to those documents and the default icon of the frame of the documents. The application knows well the resource identifiers, so they would be perfect for identifying the doctemplates, but the base class CDocTemplate declares the member variable m_nIDResource as protected and does not have any member function to get the value read.

With a little C++ trick, we can extract the desired member variable without being constricted to use a custom CDocTemplate derived class for our doctemplates.

The function(s)

UINT AfxGetDocTemplateId(CDocTemplate* pDocTemplate)
{
    // Helper class to extract the m_nIDResource member
    class CHelperDocTemplate : public CDocTemplate
    {
    public:
        CHelperDocTemplate():CDocTemplate(0, NULL, NULL, NULL){}
        UINT GetResourceId(){return m_nIDResource;}
    };
    return  ((CHelperDocTemplate*)pDocTemplate)->GetResourceId();
}


CDocTemplate* AfxFindDocTemplate(UINT nIDResource)
{
    POSITION pos = AfxGetApp()->GetFirstDocTemplatePosition();
    while ( pos )
    {
        CDocTemplate* pDocTemplate = AfxGetApp()->GetNextDocTemplate(pos);
        if ( AfxGetDocTemplateId(pDocTemplate) == nIDResource )
            return pDocTemplate;
    }
    return NULL; // Not found
}

Notice that the helper class is declared in the function body, i.e. it is a local class. In this way, it does not clutter the namespace of the application. The helper class must declare a constructor because CDocTemplate does not have a default constructor. Finally a static member function in the class cannot access the protected member variables of the base class, so a non static member function and the cast are needed.

Using the code

I named the function like the MFC global functions because it really is a little function which is missing from MFC ones. Because it is a global function, you can use it anywhere in the program, just include the header file and add the implementation file to the project. I usually include such a header at the end of the StdAfx.h file and don't think to it anymore.

So just grab it and mail me know if you appreciated it!

History

  • Submitted 29 October 2003

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here

Share

About the Author

Alessandro Forcella

United States United States
No Biography provided

Comments and Discussions

 
GeneralNice solution. Pinmembertischerr19-May-11 10:39 
GeneralVery Nice Pinmemberaaronmhawkins21-Jan-08 17:29 
AnswerRe: Very Nice Pinmembervisualc30-Jan-08 2:52 
GeneralRe: Very Nice Pinmemberaaronmhawkins30-Jan-08 5:36 
GeneralExactly what I needed PinmemberRolando E. Cruz-Marshall4-Nov-03 4:52 
GeneralNice trick ! Pinmemberemilio_g29-Oct-03 23:55 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Mobile
Web04 | 2.8.140814.1 | Last Updated 30 Oct 2003
Article Copyright 2003 by Alessandro Forcella
Everything else Copyright © CodeProject, 1999-2014
Terms of Service
Layout: fixed | fluid