Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
CODE PROJECT For Those Who Code
  • Home
  • Articles
  • FAQ
Community
  1. Home
  2. General Programming
  3. C / C++ / MFC
  4. Problem with Domodal overide behavior

Problem with Domodal overide behavior

Scheduled Pinned Locked Moved C / C++ / MFC
oophelpworkspace
6 Posts 3 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • T Offline
    T Offline
    tom groezer
    wrote on last edited by
    #1

    I have written the below code in the InitInstance method of application class I have overwridden the dailog behavior by removing ok and cancel button and also by overiding the deafult behavior of esc and return virtual key down messages. Now the problem is that I want to have control such that the lines after dlg.DoModal();</ are executed as they are the lines that kill the dialog. he basic requirement to to kill the dialog only when a particular exe is executed. I'm waiting for this process to complete but that line is after DoModal after which the control is not going. if (!CreateProcess(NULL, /* No module name (use command line). */ theApp.m_lpCmdLine, /* Command line. */ NULL, /* Process handle not inheritable. */ NULL, /* Thread handle not inheritable. */ FALSE, /* Set handle inheritance to FALSE. */ CREATE_NO_WINDOW, /* Do not display console window */ NULL, /* Use parent's environment block. */ NULL, /* Use parent's starting directory. */ &si, /* Pointer to STARTUPINFO structure. */ &pi)) /* Pointer to PROCESS_INFORMATION structure. */ status = GetLastError(); CProgressActivityDlg dlg; m_pMainWnd = &dlg; //INT_PTR nResponse = **dlg.DoModal();** //if (nResponse == IDOK) //{ // TODO: Place code here to handle when the dialog is // dismissed with OK //} //else if (nResponse == IDCANCEL) //{ // TODO: Place code here to handle when the dialog is // dismissed with Cancel //} MessageBox(NULL, _T("Before loop"), _T("Test"), MB_OK); WaitForSingleObject(pi.hProcess, INFINITE); MessageBox(NULL, _T("Out of loop"), _T("Test"), MB_OK); CloseHandle(pi.hProcess); CloseHandle(pi.hThread); PostMessageW(dlg.GetSafeHwnd(), WM_CLOSE ,0, 0); // Since the dialog has been closed, return FALSE so that we exit the // application, rather than start the application's message pump. AfxGetMainWnd()->PostMessage(WM_CLOSE, 0, 0); return FALSE;

    M 2 Replies Last reply
    0
    • T tom groezer

      I have written the below code in the InitInstance method of application class I have overwridden the dailog behavior by removing ok and cancel button and also by overiding the deafult behavior of esc and return virtual key down messages. Now the problem is that I want to have control such that the lines after dlg.DoModal();</ are executed as they are the lines that kill the dialog. he basic requirement to to kill the dialog only when a particular exe is executed. I'm waiting for this process to complete but that line is after DoModal after which the control is not going. if (!CreateProcess(NULL, /* No module name (use command line). */ theApp.m_lpCmdLine, /* Command line. */ NULL, /* Process handle not inheritable. */ NULL, /* Thread handle not inheritable. */ FALSE, /* Set handle inheritance to FALSE. */ CREATE_NO_WINDOW, /* Do not display console window */ NULL, /* Use parent's environment block. */ NULL, /* Use parent's starting directory. */ &si, /* Pointer to STARTUPINFO structure. */ &pi)) /* Pointer to PROCESS_INFORMATION structure. */ status = GetLastError(); CProgressActivityDlg dlg; m_pMainWnd = &dlg; //INT_PTR nResponse = **dlg.DoModal();** //if (nResponse == IDOK) //{ // TODO: Place code here to handle when the dialog is // dismissed with OK //} //else if (nResponse == IDCANCEL) //{ // TODO: Place code here to handle when the dialog is // dismissed with Cancel //} MessageBox(NULL, _T("Before loop"), _T("Test"), MB_OK); WaitForSingleObject(pi.hProcess, INFINITE); MessageBox(NULL, _T("Out of loop"), _T("Test"), MB_OK); CloseHandle(pi.hProcess); CloseHandle(pi.hThread); PostMessageW(dlg.GetSafeHwnd(), WM_CLOSE ,0, 0); // Since the dialog has been closed, return FALSE so that we exit the // application, rather than start the application's message pump. AfxGetMainWnd()->PostMessage(WM_CLOSE, 0, 0); return FALSE;

      M Offline
      M Offline
      Mark Salsbery
      wrote on last edited by
      #2

      tom groezer wrote:

      I'm waiting for this process to complete but that line is after DoModal after which the control is not going.

      This really isn't going to work as designed. If you insist on using a modal dialog, you'd have to poll for completion from within the dialog class...not a very good design. As with any other lengthy process, you should be waiting for completion on another thread so you don't block the UI thread. If you need the UI to be in a modal state until completion, there's a variety of ways to design the code. A couple examples: 1) Wrap the waiting worker thread in a modal dialog class. When the thread completes, it can notify the dialog (with a posted message) and the dialog can close itself. 2) Disable the UI so the user can't do anything during the process (if necessary), create a modeless dialog, and fire off the worker thread. When the thread completes, it can notify the UI thread, at which time the UI thread can destroy the modeless dialog and re-enable the UI. However you design it, the main point is - blocking the UI thread for any lengthy process (anything over a few seconds - some would say even less) is bad design, so lengthy processes should be done on threads separate from the UI thread. Mark

      Mark Salsbery Microsoft MVP - Visual C++ :java:

      1 Reply Last reply
      0
      • T tom groezer

        I have written the below code in the InitInstance method of application class I have overwridden the dailog behavior by removing ok and cancel button and also by overiding the deafult behavior of esc and return virtual key down messages. Now the problem is that I want to have control such that the lines after dlg.DoModal();</ are executed as they are the lines that kill the dialog. he basic requirement to to kill the dialog only when a particular exe is executed. I'm waiting for this process to complete but that line is after DoModal after which the control is not going. if (!CreateProcess(NULL, /* No module name (use command line). */ theApp.m_lpCmdLine, /* Command line. */ NULL, /* Process handle not inheritable. */ NULL, /* Thread handle not inheritable. */ FALSE, /* Set handle inheritance to FALSE. */ CREATE_NO_WINDOW, /* Do not display console window */ NULL, /* Use parent's environment block. */ NULL, /* Use parent's starting directory. */ &si, /* Pointer to STARTUPINFO structure. */ &pi)) /* Pointer to PROCESS_INFORMATION structure. */ status = GetLastError(); CProgressActivityDlg dlg; m_pMainWnd = &dlg; //INT_PTR nResponse = **dlg.DoModal();** //if (nResponse == IDOK) //{ // TODO: Place code here to handle when the dialog is // dismissed with OK //} //else if (nResponse == IDCANCEL) //{ // TODO: Place code here to handle when the dialog is // dismissed with Cancel //} MessageBox(NULL, _T("Before loop"), _T("Test"), MB_OK); WaitForSingleObject(pi.hProcess, INFINITE); MessageBox(NULL, _T("Out of loop"), _T("Test"), MB_OK); CloseHandle(pi.hProcess); CloseHandle(pi.hThread); PostMessageW(dlg.GetSafeHwnd(), WM_CLOSE ,0, 0); // Since the dialog has been closed, return FALSE so that we exit the // application, rather than start the application's message pump. AfxGetMainWnd()->PostMessage(WM_CLOSE, 0, 0); return FALSE;

        M Offline
        M Offline
        Mark Salsbery
        wrote on last edited by
        #3

        Here's an example of method 1 in my previous post:

        //--------------------------------------
        // IDD_PROCESSWAITER dialog resource
        //--------------------------------------

        IDD_PROCESSWAITER DIALOGEX 0, 0, 193, 50
        STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION
        CAPTION "Waiting..."
        FONT 8, "MS Shell Dlg", 400, 0, 0x1
        BEGIN
        CTEXT "Waiting for process to complete...",IDC_STATIC,7,17,179,8
        END

        //--------------------------------------
        // ProcessWaiter.h
        //--------------------------------------

        #pragma once

        // CProcessWaiter dialog

        class CProcessWaiter : public CDialog
        {
        DECLARE_DYNAMIC(CProcessWaiter)

        CString ProcessPathname;
        
        static UINT \_\_cdecl ProcessCreatorAndWaiterThread(LPVOID pParam);
        

        public:
        CProcessWaiter(CWnd* pParent = NULL); // standard constructor
        virtual ~CProcessWaiter();

        INT\_PTR ExecuteProcessAndWait(LPCTSTR pathname);
        

        // Dialog Data
        enum { IDD = IDD_PROCESSWAITER };

        protected:
        virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support

        DECLARE\_MESSAGE\_MAP()
        

        protected:
        virtual BOOL OnInitDialog();
        virtual void OnOK();
        virtual void OnCancel();
        afx_msg LRESULT OnThreadComplete(WPARAM wParam, LPARAM lParam);
        };

        //--------------------------------------
        // ProcessWaiter.cpp
        //--------------------------------------

        // ProcessWaiter.cpp : implementation file
        //

        #include "stdafx.h"
        #include "ProcessWaiter.h"

        #define WMX_THREADCOMPLETE (WM_APP + 42)

        // CProcessWaiter dialog

        IMPLEMENT_DYNAMIC(CProcessWaiter, CDialog)

        CProcessWaiter::CProcessWaiter(CWnd* pParent /*=NULL*/)
        : CDialog(CProcessWaiter::IDD, pParent)
        {
        }

        CProcessWaiter::~CProcessWaiter()
        {
        }

        INT_PTR CProcessWaiter::ExecuteProcessAndWait(LPCTSTR pathname)
        {
        ProcessPathname = pathname;

        return DoModal();
        

        }

        UINT __cdecl CProcessWaiter::ProcessCreatorAndWaiterThread(LPVOID pParam)
        {
        CProcessWaiter *pThis = (CProcessWaiter*) pParam;

        PROCESS\_INFORMATION ProcessInfo;
        STARTUPINFO StartupInfo;
        memset(&StartupInfo, 0, sizeof(STARTUPINFO));
        StartupInfo.cb = sizeof(STARTUPINFO);  
        
        if (0 != ::CreateProcess(pThis->ProcessPathname,//  LPCTSTR lpApplicationName,
        						NULL,					//  LPTSTR lpCommandLine,
        						NULL,					//  LPSECURITY\_ATTRIBUTES lpProcessAttributes,
        						NULL,					//  LPSECURITY\_ATTRIBUTES lpThreadAttributes,
        						FALSE,					//  BOOL bInheritHandles,
        						NORMAL\_PRIORITY\_CLASS,	//  DWORD dwCreationFlags,
        						NULL
        
        N 1 Reply Last reply
        0
        • M Mark Salsbery

          Here's an example of method 1 in my previous post:

          //--------------------------------------
          // IDD_PROCESSWAITER dialog resource
          //--------------------------------------

          IDD_PROCESSWAITER DIALOGEX 0, 0, 193, 50
          STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | WS_POPUP | WS_CAPTION
          CAPTION "Waiting..."
          FONT 8, "MS Shell Dlg", 400, 0, 0x1
          BEGIN
          CTEXT "Waiting for process to complete...",IDC_STATIC,7,17,179,8
          END

          //--------------------------------------
          // ProcessWaiter.h
          //--------------------------------------

          #pragma once

          // CProcessWaiter dialog

          class CProcessWaiter : public CDialog
          {
          DECLARE_DYNAMIC(CProcessWaiter)

          CString ProcessPathname;
          
          static UINT \_\_cdecl ProcessCreatorAndWaiterThread(LPVOID pParam);
          

          public:
          CProcessWaiter(CWnd* pParent = NULL); // standard constructor
          virtual ~CProcessWaiter();

          INT\_PTR ExecuteProcessAndWait(LPCTSTR pathname);
          

          // Dialog Data
          enum { IDD = IDD_PROCESSWAITER };

          protected:
          virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support

          DECLARE\_MESSAGE\_MAP()
          

          protected:
          virtual BOOL OnInitDialog();
          virtual void OnOK();
          virtual void OnCancel();
          afx_msg LRESULT OnThreadComplete(WPARAM wParam, LPARAM lParam);
          };

          //--------------------------------------
          // ProcessWaiter.cpp
          //--------------------------------------

          // ProcessWaiter.cpp : implementation file
          //

          #include "stdafx.h"
          #include "ProcessWaiter.h"

          #define WMX_THREADCOMPLETE (WM_APP + 42)

          // CProcessWaiter dialog

          IMPLEMENT_DYNAMIC(CProcessWaiter, CDialog)

          CProcessWaiter::CProcessWaiter(CWnd* pParent /*=NULL*/)
          : CDialog(CProcessWaiter::IDD, pParent)
          {
          }

          CProcessWaiter::~CProcessWaiter()
          {
          }

          INT_PTR CProcessWaiter::ExecuteProcessAndWait(LPCTSTR pathname)
          {
          ProcessPathname = pathname;

          return DoModal();
          

          }

          UINT __cdecl CProcessWaiter::ProcessCreatorAndWaiterThread(LPVOID pParam)
          {
          CProcessWaiter *pThis = (CProcessWaiter*) pParam;

          PROCESS\_INFORMATION ProcessInfo;
          STARTUPINFO StartupInfo;
          memset(&StartupInfo, 0, sizeof(STARTUPINFO));
          StartupInfo.cb = sizeof(STARTUPINFO);  
          
          if (0 != ::CreateProcess(pThis->ProcessPathname,//  LPCTSTR lpApplicationName,
          						NULL,					//  LPTSTR lpCommandLine,
          						NULL,					//  LPSECURITY\_ATTRIBUTES lpProcessAttributes,
          						NULL,					//  LPSECURITY\_ATTRIBUTES lpThreadAttributes,
          						FALSE,					//  BOOL bInheritHandles,
          						NORMAL\_PRIORITY\_CLASS,	//  DWORD dwCreationFlags,
          						NULL
          
          N Offline
          N Offline
          Nelek
          wrote on last edited by
          #4

          Nice example :)

          Greetings. -------- M.D.V. ;) If something has a solution... Why do we have to worry about?. If it has no solution... For what reason do we have to worry about? Help me to understand what I'm saying, and I'll explain it better to you “The First Rule of Program Optimization: Don't do it. The Second Rule of Program Optimization (for experts only!): Don't do it yet.” - Michael A. Jackson

          T 1 Reply Last reply
          0
          • N Nelek

            Nice example :)

            Greetings. -------- M.D.V. ;) If something has a solution... Why do we have to worry about?. If it has no solution... For what reason do we have to worry about? Help me to understand what I'm saying, and I'll explain it better to you “The First Rule of Program Optimization: Don't do it. The Second Rule of Program Optimization (for experts only!): Don't do it yet.” - Michael A. Jackson

            T Offline
            T Offline
            tom groezer
            wrote on last edited by
            #5

            Is it ok to have something like below to be posted. I just wanted to know whether passing WM_CLOSE is good enough as EndDialog(); PostMessage((((CProgressActivityApp*)lpParam)->m_pMainWnd)->GetSafeHwnd(), WM_CLOSE, 0, 0);

            M 1 Reply Last reply
            0
            • T tom groezer

              Is it ok to have something like below to be posted. I just wanted to know whether passing WM_CLOSE is good enough as EndDialog(); PostMessage((((CProgressActivityApp*)lpParam)->m_pMainWnd)->GetSafeHwnd(), WM_CLOSE, 0, 0);

              M Offline
              M Offline
              Mark Salsbery
              wrote on last edited by
              #6

              Yes it's ok. The problem is, your code will never get there to post the message until the dialog closes, which isn't going to happen :) Mark

              Mark Salsbery Microsoft MVP - Visual C++ :java:

              1 Reply Last reply
              0
              Reply
              • Reply as topic
              Log in to reply
              • Oldest to Newest
              • Newest to Oldest
              • Most Votes


              • Login

              • Don't have an account? Register

              • Login or register to search.
              • First post
                Last post
              0
              • Categories
              • Recent
              • Tags
              • Popular
              • World
              • Users
              • Groups