X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/2b5f62a0b2db198609b45dec622a018dae37008e..29281095c4959cbadfcc66efccf679c6c25c7dc7:/src/os2/dialog.cpp diff --git a/src/os2/dialog.cpp b/src/os2/dialog.cpp index 1ab046a28e..fb4e903b07 100644 --- a/src/os2/dialog.cpp +++ b/src/os2/dialog.cpp @@ -24,6 +24,8 @@ #include "wx/os2/private.h" #include "wx/log.h" +#include "wx/evtloop.h" +#include "wx/ptr_scpd.h" #define wxDIALOG_DEFAULT_X 300 #define wxDIALOG_DEFAULT_Y 300 @@ -31,8 +33,6 @@ #define wxDIALOG_DEFAULT_WIDTH 500 #define wxDIALOG_DEFAULT_HEIGHT 500 -wxWindowList wxModalDialogs; - IMPLEMENT_DYNAMIC_CLASS(wxDialog, wxTopLevelWindow) BEGIN_EVENT_TABLE(wxDialog, wxDialogBase) @@ -44,11 +44,47 @@ BEGIN_EVENT_TABLE(wxDialog, wxDialogBase) EVT_CLOSE(wxDialog::OnCloseWindow) END_EVENT_TABLE() +// ---------------------------------------------------------------------------- +// wxDialogModalData +// ---------------------------------------------------------------------------- + +// this is simply a container for any data we need to implement modality which +// allows us to avoid changing wxDialog each time the implementation changes +class wxDialogModalData +{ +public: + wxDialogModalData(wxDialog *dialog) : m_evtLoop(dialog) { } + + void RunLoop() + { + m_evtLoop.Run(); + } + + void ExitLoop() + { + m_evtLoop.Exit(); + } + +private: + wxModalEventLoop m_evtLoop; +}; + +wxDEFINE_TIED_SCOPED_PTR_TYPE(wxDialogModalData); + +// ============================================================================ +// implementation +// ============================================================================ + +// ---------------------------------------------------------------------------- +// wxDialog construction +// ---------------------------------------------------------------------------- + void wxDialog::Init() { m_pOldFocus = (wxWindow *)NULL; m_isShown = FALSE; m_pWindowDisabler = (wxWindowDisabler *)NULL; + m_modalData = NULL; SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_3DFACE)); } // end of wxDialog::Init @@ -62,14 +98,6 @@ bool wxDialog::Create( , const wxString& rsName ) { - long lX = rPos.x; - long lY = rPos.y; - long lWidth = rSize.x; - long lHeight = rSize.y; - const char* zDlg; - WXDWORD dwExtendedStyle = 0L; - HWND hWnd; - Init(); SetExtraStyle(GetExtraStyle() | wxTOPLEVEL_EX_DIALOG); @@ -169,7 +197,7 @@ bool wxDialog::IsModal() const bool wxDialog::IsModalShowing() const { - return wxModalDialogs.Find((wxDialog *)this) != NULL; // const_cast + return m_modalData != NULL; // const_cast } // end of wxDialog::IsModalShowing void wxDialog::DoShowModal() @@ -181,7 +209,6 @@ void wxDialog::DoShowModal() wxCHECK_RET( !IsModalShowing(), _T("DoShowModal() called twice") ); wxCHECK_RET( IsModal(), _T("can't DoShowModal() modeless dialog") ); - wxModalDialogs.Append(this); if (pOldFocus) hWndOldFocus = (HWND)pOldFocus->GetHWND(); @@ -200,12 +227,6 @@ void wxDialog::DoShowModal() // wxASSERT_MSG(!m_pWindowDisabler, _T("disabling windows twice?")); - // - // Disables other app windows and window proc message processing - // until WinDismissDlg called - // - ::WinProcessDlg((HWND)GetHwnd()); - // // Before entering the modal loop, reset the "is in OnIdle()" flag (see // comment in app.cpp) @@ -215,25 +236,16 @@ void wxDialog::DoShowModal() gbInOnIdle = FALSE; - // - // Enter the modal loop - // - while ( IsModalShowing() ) + // enter the modal loop { -#if wxUSE_THREADS - wxMutexGuiLeaveOrEnter(); -#endif // wxUSE_THREADS - - while ( !wxTheApp->Pending() && wxTheApp->ProcessIdle() ) - ; - - // a message came or no more idle processing to do - wxTheApp->DoMessage(); + wxDialogModalDataTiedPtr modalData(&m_modalData, + new wxDialogModalData(this)); + modalData->RunLoop(); } gbInOnIdle = bWasInOnIdle; // - // Snd restore focus + // and restore focus // Note that this code MUST NOT access the dialog object's data // in case the object has been deleted (which will be the case // for a modal dialog that has been destroyed before calling EndModal). @@ -265,6 +277,8 @@ bool wxDialog::Show( delete m_pWindowDisabler; m_pWindowDisabler = NULL; } + if ( m_modalData ) + m_modalData->ExitLoop(); } // @@ -280,6 +294,14 @@ bool wxDialog::Show( if (bShow) { + // dialogs don't get WM_SIZE message after creation unlike most (all?) + // other windows and so could start their life non laid out correctly + // if we didn't call Layout() from here + // + // NB: normally we should call it just the first time but doing it + // every time is simpler than keeping a flag +// Layout(); + // // Usually will result in TransferDataToWindow() being called // @@ -310,14 +332,6 @@ bool wxDialog::Show( } DoShowModal(); } - else // end of modal dialog - { - // - // This will cause IsModalShowing() return FALSE and our local - // message loop will terminate - // - wxModalDialogs.DeleteObject(this); - } } return TRUE; } // end of wxDialog::Show @@ -341,7 +355,6 @@ void wxDialog::EndModal( { SetReturnCode(nRetCode); Show(FALSE); - ::WinDismissDlg((HWND)GetHwnd(), nRetCode); } // end of wxDialog::EndModal // ----------------------------------------------------------------------------