Dynamic Creation of Thread-Separated Dialogs Having Only Its Class Name


This article describes a way of creating class objects by the name of its classes. This way permits you to create a new class object by calling a function or class method that receives as input parameters a pointer to the CRuntimeClass object. Thus, this method encapsulates the procedure of object creation inside another class or function.

In general, the article demonstrates how to design a mechanism that creates a user-selected dialog window in its own child thread. The child thread class is derived from CWinThread and its InitInstanse method encapsulates the procedure of object creation. A user can choose a type of dialog that is to be created.

The project architecture represented in Figure 1.

Figure 1. Project Architecture

Writing a Dialog Class

For dialog class creation, we can use a standard VC++ wizard. All we need to do is enter class name and choose the class that it is derived from. The first step is to adapt the newly created class to the correct MFC macros DECLARE_DYNAMIC and IMPLEMENT_DYNAMIC to DECLARE_DYNCREATE and IMPLEMENT_DYNCREATE in ".h" and ".cpp" files of class.

Use of the DECLARE_DYNCREATE macro in ".h" and the IMPLEMENT_DYNCREATE macro in ".cpp" permits classes to be created by the framework dynamically at run time.

The class should look like the following:

class CDialog1 : public CDialog

   CDialog1(CWnd* pParent = NULL);   // standard constructor
   virtual ~CDialog1();

// Dialog Data
   enum { IDD = IDD_DIALOG1 };

   afx_msg void OnClose();

It is convenient to add a WM_CLOSE event handler method to notify the thread which dialog is attached to the window that is going to be closed and it is necessary to call the ExitInstanse method. To let the thread know about this intention, the window has to send a WM_QUIT message.

void CDialog1::OnClose()
   this->PostMessage( WM_QUIT );


Writing a Child Thread Class

We also can create this class with the help of the VC++ class wizard; just set the derived class to CWinThread. It is necessary to repeat the procedure of changing the MFC macros DECLARE_DYNAMIC and IMPLEMENT_DYNAMIC to DECLARE_DYNCREATE and IMPLEMENT_DYNCREATE in the ".h" and ".cpp" files of the class. This class also is to be created dynamically at run time.

Obviously, we need some variables: pointer to dialog, dialog ID, pointer to CRuntimeClass object of attached dialog class.

class CChildThread : public CWinThread
   friend class CMainFrame;

CChildThread( CRuntimeClass* pClass = NULL, UINT id = 0 );
   virtual ~CChildThread();

   CRuntimeClass* m_pClass;
   UINT m_ID;

   CDialog* m_pDialog;

   virtual BOOL InitInstance();
   virtual int ExitInstance();


The class constructor ought to be modified to get some class variable values from input parameters. We can initialise the pointer to CRuntimeClass and dialog ID.

CChildThread::CChildThread( CRuntimeClass* pClass, UINT id )
   m_pClass  = pClass;
   m_ID      = id;
   m_pDialog = NULL;

Now, when the thread object already exists, the InitInstanse method might be called. The mechanism of class object creation by name is placed into this function.

BOOL CChildThread::InitInstance()
   if ( m_pClass != NULL)
      CObject* pObject = m_pClass->CreateObject();

      if ( pObject->IsKindOf( RUNTIME_CLASS( CDialog ) ) )
         CWnd desktop;
         desktop.Attach( ::GetDesktopWindow() );

         m_pDialog = ( CDialog* )pObject;
         m_pDialog->Create( m_ID, &desktop );

         m_pMainWnd   = m_pDialog;
         m_pActiveWnd = m_pDialog;
         m_pMainWnd->ShowWindow( SW_SHOW );


   return TRUE;

First, the object will be created by using the CreateObject method of the CRuntimeClass class. Second, we should convince that just-created object is derived from CDialog using the IsKindOf method of the CObject class. And finally, the Create method of the CDialog class might be called.

The ExitInstance method of the class is to be extended. You should process such an operation like destroying the attached dialog.

int CChildThread::ExitInstance()
   if ( m_pDialog != NULL)
      delete m_pDialog;
      m_pDialog = NULL;

   return CWinThread::ExitInstance();

Using a Class of the Child Thread Type

When a user performs actions to create a new dialog window by dialog selecting, we must take care of the handler that catches this event.

void CSampleDlg::OnDialogDialog1()
   CChildThread* pThread = new CChildThread(
                 RUNTIME_CLASS( CDialog1 ), IDD_DIALOG1 );

   m_aChildThreads.Add( pThread );

All we have to do is dynamically create a new CChildThread object, passing as input parameters to its constructor a pointer to the CRuntimeClass object and to call the CreateThread method of the newly created thread object. For convenience of subsequent destroying, the thread object pointers are to be stored in a special array. This array is useful when the application main window is going to be closed.

void CSampleDlg::OnClose()
   for ( int i = 0; i < m_aChildThreads.GetSize(); i++ )
      if ( m_aChildThreads[i]->GetThreadPriority()




Thus, it was cleared how to create a class object having only its class name and why this mechanism is needed. This project model is convenient to use when designing a multi thread application with a set of fixed dialog types when each thread has its own message queue. This model permits you to create windows with equal priority of overlapping. Nevertheless, there is an unresolved task to manage a behaviour of such dialogs, to control operations of minimise and restore.

The idea of using one child thread class for all types of dialogs is original. It actually optimises the project architecture when it is used in a thread-separated dialog.



  • How to Send Data to the Dialog

    Posted by GuenniAtWork on 07/21/2005 08:52am

    How can i put data from the Main Dialog to the Thread Dialog?

  • Re:G? Posted by gang5310 on 04/06/2004 09:52pm

    Re:G? Reply

Leave a Comment
  • Your email address will not be published. All fields are required.

Top White Papers and Webcasts

  • Migrating away from Windows Server 2003 is an investment in your organization's future, and there has never been a better time to begin the migration process. Take the next step to transform your datacenter by upgrading your server platform with leading edge Windows Operating Systems and SanDisk flash solutions.

  • Today, users, applications, and data exist in more places than ever before, creating an unprecedented challenge for IT. How can IT achieve the flexibility and agility it needs to offer multiple types of applications in multiple locations? To better serve business demands for information everywhere, enterprises must develop new strategies for optimizing multiple kinds of networks. Read this white paper to learn how hybrid networks provide an unprecedented level of network dynamism, enterprise agility, and the …

Most Popular Programming Stories

More for Developers

RSS Feeds

Thanks for your registration, follow us on our social networks to keep up-to-date