Common Dialog Templates - Create a WinZip Style File Add Dialog
Using templates and subclassing to create fully-featured dialogs
This sample, from Cayce Cochran (firstname.lastname@example.org), demonstrates how to use a dialog template with a File Open or Save CommonDialog. It takes advantage of the CommonDialog/Direct DLL component which now (versions dated 1 November 1999 and higher) includes the relevant support for templates.
About Dialog Templates
A dialog template is a concept popular in C and C++ coding. Basically they work like a really rubbish version of VB: you lay out the components of the resource in some sort of WYSIWYG environment, which is then written to a resource. When you come to show the dialog box in the C or C++ program, you pass in the dialog template resource and the appropriate functions are invoked to create the specified controls on your dialog for you.
Templates can be created quite easily if you have a Resource Editor tool (such as the ones provided with the C and C++ environments in Visual Studio, which will even import a VB form for you and spit out the equivalent dialog template). If you're feeling particularly in the mood for this sort of functionality then you should see it isn't particularly difficult to create your own by hand. Look at the files WAdlgres.rc and Resource.h in the download for hints on the format of a template.
Resources And VB
The first problem is the fact that the Common Dialog template function requires the template to be included in a resource in the executable. However, resources in VB apps are hidden from the API functions whilst you are debugging the app in IDE (you can only read VB resources in the IDE using the standard VB resource functions LoadResPicture, LoadResData and LoadResString).
Incidentally, in version 6 of you could debug VC++ projects in a very similar way to Visual Basic ones, it seems a shame that this sort of functionality was never provided for Visual Basic (and is actually retrograded in .NET). Resources aren't the only example of VB messing around with stuff behind the scenes. More annoying is what happens to your COM object's CLSIDs in the IDE...
Anyway, this problem is easy to work around by compiling the resource into a DLL and then using that when working in the IDE. The easiest way to do this is to create a VB ActiveX DLL project, add the .RES file to it and compile that (you may want to add a dummy method to the default Class1 just to give VB something to do when creating it).
Determining whether you are in the IDE or not is achieved using the classic Debug.Assert check:
Private m_bInIDE As Boolean Public Property Get InIDE() As Boolean Debug.Assert (IsInIDE) InIDE = m_bInIDE End Property Private Property Get IsInIDE() As Boolean m_bInIDE = True IsInIDE = True End Property
Because Debug.Assert code is only run when you are in the IDE, when the code is compiled the IsInIDE property is never called, and therefore the m_bInIDE property is never set to True.
CommonDialog/Direct and Dialog Templates
Telling the CommonDialog/Direct library to use a dialog template when it is shown is achieved by setting two properties:
Because you probably need to know the value of any additional controls in your template, you should set the CommonDialog/Direct HookDialog flag to True. Having done this the class will raise InitDialog and WMCommand events, which you can use to populate controls and respond to changes in their values.