• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 230
  • Last Modified:

Dynamic Docuemnt Templates in MDI

I'm writing an MFC app that can handle a number of different file types.

I want the user to be able to decide which file formats they want to use.

The easiest way I thought of doing this is to place each document template and view document classes in separate DLLs, like a sort of MFC extension DLL, and the user can place the ones they require in the app directory.

Doing it this way means that the DLLs can't be linked to the app when it is compiled as the DLLs that will be used aren't know at this time.

Is this the best way of doing it and is it possible?

Thanks

Gavin Rouse
0
gav061697
Asked:
gav061697
  • 9
  • 7
1 Solution
 
jkrCommented:
It is possible. I'm not sure whether it is the best way, but it's at least a good one.
>>Doing it this way means that the DLLs can't be linked to the
>>app when it is compiled as the DLLs that will be used aren't
>>know at this time.
As 'CMultiDocTemplate' is always known, you can do it this way:
Implement a function in the DLL that does the following:

__declspec (dllexport)
CMultiDocTemplate* DllGetDocTemplate()
{
      CMultiDocTemplate* pTemplate;
      pOeTemplate = new CMultiDocTemplate(
            IDR_MYTEMPLATE,
            RUNTIME_CLASS(CMyTemplate),
            RUNTIME_CLASS(CChildFrame), // custom MDI child frame
            RUNTIME_CLASS(CMyTemplatesView));

return ( pTemplate);
}

0
 
jkrCommented:
Ooops, i forgot about the apllication's part:

typedef CMultiDocTemplate* ( *PDLLGETDOCTEMPLATE)();
HANDLE hDll = LoadLibrary( "mydoctpl.dll");
PDLLGETDOCTEMPLATE pGetTemplate = (PDLLGETDOCTEMPLATE) GetProcAddress( hDll, "DllGetDocTemplate);

CMultiDocTemplate* pTemplate = (pGetTemplate)();

      AddDocTemplate(pTemplate);

      // Connect the COleTemplateServer to the document template.
      //  The COleTemplateServer creates new documents on behalf
      //  of requesting OLE containers by using information
      //  specified in the document template.

      m_server.ConnectTemplate( clsid, pTemplate, FALSE);


0
 
jkrCommented:
OK - i just noticed that there are several tasks to do (e.g. using a .def file so that 'DllGetDocTemplate()' is exported using the correct name and a function that retrieves the DLL's clsid from the DLL), so feel free to ask if you have further qestions regarding this issue...
0
Concerto's Cloud Advisory Services

Want to avoid the missteps to gaining all the benefits of the cloud? Learn more about the different assessment options from our Cloud Advisory team.

 
gav061697Author Commented:
There's actually a MFC example which I found in the help files called DLLHusk which does exactly what I want in the same way that you described.

However, my version works fine in Debug mode, but when I try the Release version my program crashes in the InitDLL function at the AddDocTemplate call (see the DLLHusk example if you're not sure what I mean).  The only difference with my code is that the classes are in separte files rather than all in one.

Do you know what might cause the problem.

My first thought was that the GetProcAddress() call was returning the wrong address as the crash seemed to occur in the RichEditCtrl source file.  However, I mangaed to partly debug my code and it gets to the AddDocTemplate call then goes to two source files which it shouldn't (BarDock.cpp and the RichEdit source file)

I can provide the source code if you want it.
0
 
jkrCommented:
I assume that there are problems regarding the runtime class information - if you could provide some source code, this could be a great help ;-)
0
 
jkrCommented:
Hmm - your DLL is created as a MFC extension DLL, isn't it?
0
 
gav061697Author Commented:
How should I give it to you?

>> Hmm - your DLL is created as a MFC extension DLL, isn't it?
Yes
0
 
gav061697Author Commented:
How should I give it to you?

>> Hmm - your DLL is created as a MFC extension DLL, isn't it?
Yes
0
 
jkrCommented:
The best thing would be if you post the relevant parts...
0
 
gav061697Author Commented:
Here's my InitDLL() function

// Exported DLL initialization is run in context of running application
extern "C" void WINAPI InitDLL()
{
      TRACE0("DOCVIEW.DLL: InitDLL()\n");

      // create a new CDynLinkLibrary for this app
      new CDynLinkLibrary(DocViewDLL);

      // Register the doc templates we provide to the app
      CWinApp* pApp = AfxGetApp();
      ASSERT(pApp != NULL);

      /* Release crashes here */
      pApp->AddDocTemplate(new CMultiDocTemplate(IDR_VCTYPE,
                  RUNTIME_CLASS(CVCDoc),
                  RUNTIME_CLASS(CMDIChildWnd),
                  RUNTIME_CLASS(CVCView)));
      // add other initialization here
}
0
 
jkrCommented:
Hmm, seems fine at first glance... Is the app also a release version?
0
 
jkrCommented:
I'd suggest
CMultiDocTemplate* pTempl= CMultiDocTemplate(IDR_VCTYPE,
RUNTIME_CLASS(CVCDoc),
RUNTIME_CLASS(CMDIChildWnd),
RUNTIME_CLASS(CVCView));

if ( !pTempl) AfxMessageBox( ...);

pApp->AddDocTemplate( pTempl);

to find out whether the problem is related to the template or the call...
0
 
gav061697Author Commented:
I think i've found the problem...in the release version pApp == NULL

I don't know why...i'll try and look into it further...if you have any ideas let me know

Thanks
0
 
jkrCommented:
The most common reason for this: Is the app also a release version? If not, you might want to test it using a release version of the application, as mixing debug/release usually leads into trouble...
0
 
gav061697Author Commented:
i'll try that..

thiscode  may/may not help...it's how I load and call the InitDLL() function:

HINSTANCE hInstance = AfxLoadLibrary("docview\\release\\docview.dll");
FARPROC farproc = GetProcAddress( hInstance, "InitDLL" );
if(farproc != NULL)
     farproc();
else
     AfxMessageBox("Can't find InitDLL() function.");

0
 
gav061697Author Commented:
just tried it...works fine now...how annoying...thanks for your help..

have some points :-)
0

Featured Post

What does it mean to be "Always On"?

Is your cloud always on? With an Always On cloud you won't have to worry about downtime for maintenance or software application code updates, ensuring that your bottom line isn't affected.

  • 9
  • 7
Tackle projects and never again get stuck behind a technical roadblock.
Join Now