Discussion:
Modal Dialog From Modeless Dialog
(too old to reply)
none
2012-06-19 04:52:20 UTC
Permalink
Hi all,

I have an MFC app with a main window and a bunch of modeless tool windows.
If any of these windows (the main window or any tool window) displays a
MessageBox(), only that one window is "frozen" while the dialog is open.
So, the user can just ignore the error message and click in other windows.
Is there a way to freeze all windows except for the message box, regardless
of which window actually launched the modal dialog?

I've tried all the combinations of MB_APPMODAL, MB_TASKMODAL, etc, and none
of them changed anything. And, anyway, I need something that works for any
dialog, not just a MessageBox() dialog.

Thanks.
Uwe Kotyczka
2012-06-19 08:17:07 UTC
Permalink
Post by none
Hi all,
I have an MFC app with a main window and a bunch of modeless tool windows.
If any of these windows (the main window or any tool window) displays a
MessageBox(), only that one window is "frozen" while the dialog is open.
So, the user can just ignore the error message and click in other windows.
Is there a way to freeze all windows except for the message box, regardless
of which window actually launched the modal dialog?
I've tried all the combinations of MB_APPMODAL, MB_TASKMODAL, etc, and none
of them changed anything.  And, anyway, I need something that works for any
dialog, not just a MessageBox() dialog.
Thanks.
If hWnd is the window which you wish to behave like a modal dialog,
you could use something like my GoModal function (code below).
Don't forget to call GoModal(hWnd, false) before closing the "modal"
dialog.


BOOL CALLBACK EnableWndProc(HWND hWnd, LPARAM lParam)
{
EnableWindow(hWnd, !lParam);
return TRUE;
}

bool GoModal(HWND hWnd, bool bModal)
{
HANDLE hThreadSnap;
THREADENTRY32 te32;
te32.dwSize = sizeof(te32);

DWORD dwProcessId = GetCurrentProcessId();

// create a snapshot of the system
hThreadSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0);
if (NULL == hThreadSnap)
return false;

// retrieve information about the first thread
if (!Thread32First(hThreadSnap, &te32))
{
CloseHandle(hThreadSnap);
return false;
}

// process the first thread and then get the rest of the threads.
do
{
if (te32.th32OwnerProcessID == dwProcessId)
EnumThreadWindows(te32.th32ThreadID, &EnableWndProc, bModal);
}
while (Thread32Next(hThreadSnap, &te32));

if (bModal)
{
// reenable hWnd
EnableWindow(hWnd, TRUE);
}

CloseHandle(hThreadSnap);
return true;
}

HTH
none
2012-06-22 09:03:34 UTC
Permalink
Thanks, that's a very clever way to find all of the thread's windows, but
I'm not sure I understand what you're doing to them once you find them. It
looks like you're calling EnableWindow()?

I did something similar but called BeginModalState() for all of the tool
windows. This doesn't change the windows' appearance, but essentially just
freezes them until I call EndModalState() later.

Thanks again.

Continue reading on narkive:
Loading...