1 ///////////////////////////////////////////////////////////////////////////// 
   3 // Purpose:     wxDialog class 
   4 // Author:      Stefan Csomor 
   8 // Copyright:   (c) Stefan Csomor 
   9 // Licence:       wxWindows licence 
  10 ///////////////////////////////////////////////////////////////////////////// 
  12 #if defined(__GNUG__) && !defined(NO_GCC_PRAGMA) 
  13 #pragma implementation "dialog.h" 
  16 #include "wx/wxprec.h" 
  18 #include "wx/dialog.h" 
  22 #include "wx/settings.h" 
  24 #include "wx/mac/uma.h" 
  26 // Lists to keep track of windows, so we can disable/enable them 
  28 wxList wxModalDialogs
; 
  29 //wxList wxModelessWindows;  // Frames and modeless dialogs 
  30 extern wxList wxPendingDelete
; 
  32 #if !USE_SHARED_LIBRARY 
  33 IMPLEMENT_DYNAMIC_CLASS(wxDialog
, wxTopLevelWindow
) 
  35 BEGIN_EVENT_TABLE(wxDialog
, wxDialogBase
) 
  36   EVT_BUTTON(wxID_OK
, wxDialog::OnOK
) 
  37   EVT_BUTTON(wxID_APPLY
, wxDialog::OnApply
) 
  38   EVT_BUTTON(wxID_CANCEL
, wxDialog::OnCancel
) 
  40   EVT_CHAR_HOOK(wxDialog::OnCharHook
) 
  42   EVT_SYS_COLOUR_CHANGED(wxDialog::OnSysColourChanged
) 
  44   EVT_CLOSE(wxDialog::OnCloseWindow
) 
  51     m_isModalStyle 
= false; 
  54 bool wxDialog::Create(wxWindow 
*parent
, wxWindowID id
, 
  55            const wxString
& title
, 
  61     SetExtraStyle(GetExtraStyle() | wxTOPLEVEL_EX_DIALOG
); 
  63     // All dialogs should really have this style 
  64     style 
|= wxTAB_TRAVERSAL
; 
  66     if ( !wxTopLevelWindow::Create(parent
, id
, title
, pos
, size
, style 
& ~(wxYES
|wxOK
|wxNO
|wxCANCEL
) , name
) ) 
  72 void wxDialog::SetModal(bool flag
) 
  76         m_isModalStyle 
= true; 
  78         wxModelessWindows
.DeleteObject(this); 
  80         SetWindowModality( (WindowRef
) MacGetWindowRef() , kWindowModalityAppModal 
, NULL 
) ; 
  85         m_isModalStyle 
= false; 
  87         wxModelessWindows
.Append(this); 
  93     m_isBeingDeleted 
= TRUE
; 
  97 // By default, pressing escape cancels the dialog , on mac command-stop does the same thing 
  98 void wxDialog::OnCharHook(wxKeyEvent
& event
) 
 100     if (( event
.m_keyCode 
== WXK_ESCAPE 
|| 
 101         ( event
.m_keyCode 
== '.' && event
.MetaDown() ) ) 
 102         && FindWindow(wxID_CANCEL
) ) 
 104         // Behaviour changed in 2.0: we'll send a Cancel message 
 105         // to the dialog instead of Close. 
 106         wxCommandEvent 
cancelEvent(wxEVT_COMMAND_BUTTON_CLICKED
, wxID_CANCEL
); 
 107         cancelEvent
.SetEventObject( this ); 
 108         GetEventHandler()->ProcessEvent(cancelEvent
); 
 112     // We didn't process this event. 
 116 bool wxDialog::IsModal() const 
 118     return m_isModalStyle
; 
 122 bool wxDialog::IsModalShowing() const 
 124     return wxModalDialogs
.Find((wxDialog 
*)this) != NULL
; // const_cast 
 127 bool wxDialog::Show(bool show
) 
 129     if ( !wxDialogBase::Show(show
) ) 
 137         // usually will result in TransferDataToWindow() being called 
 147         else // end of modal dialog 
 149             // this will cause IsModalShowing() return FALSE and our local 
 150             // message loop will terminate 
 151             wxModalDialogs
.DeleteObject(this); 
 159 extern bool s_macIsInModalLoop 
; 
 162 void wxDialog::DoShowModal() 
 164     wxCHECK_RET( !IsModalShowing(), _T("DoShowModal() called twice") ); 
 166     wxModalDialogs
.Append(this); 
 171     BeginAppModalStateForWindow(  (WindowRef
) MacGetWindowRef()) ; 
 173     // TODO : test whether parent gets disabled 
 174     bool formerModal 
= s_macIsInModalLoop 
; 
 175     s_macIsInModalLoop 
= true ; 
 177     while ( IsModalShowing() ) 
 179         wxTheApp
->MacDoOneEvent() ; 
 180         // calls process idle itself 
 184     EndAppModalStateForWindow( (WindowRef
) MacGetWindowRef() ) ; 
 186     // TODO probably reenable the parent window if any 
 187     s_macIsInModalLoop 
= formerModal 
; 
 192 // Replacement for Show(TRUE) for modal dialogs - returns return code 
 193 int wxDialog::ShowModal() 
 201     return GetReturnCode(); 
 204 // NB: this function (surprizingly) may be called for both modal and modeless 
 205 //     dialogs and should work for both of them 
 206 void wxDialog::EndModal(int retCode
) 
 208   SetReturnCode(retCode
); 
 213 void wxDialog::OnOK(wxCommandEvent
& WXUNUSED(event
)) 
 215   if ( Validate() && TransferDataFromWindow() ) 
 221 void wxDialog::OnApply(wxCommandEvent
& WXUNUSED(event
)) 
 224     TransferDataFromWindow(); 
 225   // TODO probably need to disable the Apply button until things change again 
 228 void wxDialog::OnCancel(wxCommandEvent
& WXUNUSED(event
)) 
 230     EndModal(wxID_CANCEL
); 
 233 void wxDialog::OnCloseWindow(wxCloseEvent
& WXUNUSED(event
)) 
 235     // We'll send a Cancel message by default, 
 236     // which may close the dialog. 
 237     // Check for looping if the Cancel event handler calls Close(). 
 239     // Note that if a cancel button and handler aren't present in the dialog, 
 240     // nothing will happen when you close the dialog via the window manager, or 
 242     // We wouldn't want to destroy the dialog by default, since the dialog may have been 
 243     // created on the stack. 
 244     // However, this does mean that calling dialog->Close() won't delete the dialog 
 245     // unless the handler for wxID_CANCEL does so. So use Destroy() if you want to be 
 246     // sure to destroy the dialog. 
 247     // The default OnCancel (above) simply ends a modal dialog, and hides a modeless dialog. 
 249     static wxList closing
; 
 251     if ( closing
.Member(this) ) 
 254     closing
.Append(this); 
 256     wxCommandEvent 
cancelEvent(wxEVT_COMMAND_BUTTON_CLICKED
, wxID_CANCEL
); 
 257     cancelEvent
.SetEventObject( this ); 
 258     GetEventHandler()->ProcessEvent(cancelEvent
); // This may close the dialog 
 260     closing
.DeleteObject(this); 
 263 void wxDialog::OnSysColourChanged(wxSysColourChangedEvent
& WXUNUSED(event
)) 
 265   SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_3DFACE
));