]> git.saurik.com Git - wxWidgets.git/blame - src/mac/carbon/dialog.cpp
Missing header.
[wxWidgets.git] / src / mac / carbon / dialog.cpp
CommitLineData
e9576ca5 1/////////////////////////////////////////////////////////////////////////////
670f9935 2// Name: src/mac/carbon/dialog.cpp
e9576ca5 3// Purpose: wxDialog class
a31a5f85 4// Author: Stefan Csomor
e9576ca5 5// Modified by:
a31a5f85 6// Created: 1998-01-01
e9576ca5 7// RCS-ID: $Id$
a31a5f85 8// Copyright: (c) Stefan Csomor
670f9935 9// Licence: wxWindows licence
e9576ca5
SC
10/////////////////////////////////////////////////////////////////////////////
11
3d1a4878
SC
12#include "wx/wxprec.h"
13
e9576ca5 14#include "wx/dialog.h"
670f9935
WS
15
16#ifndef WX_PRECOMP
17 #include "wx/app.h"
de6185e2 18 #include "wx/utils.h"
76b49cf4 19 #include "wx/frame.h"
9eddec69 20 #include "wx/settings.h"
670f9935
WS
21#endif // WX_PRECOMP
22
d497dca4 23#include "wx/mac/uma.h"
519cb848 24
efb064f7 25
e9576ca5
SC
26// Lists to keep track of windows, so we can disable/enable them
27// for modal dialogs
28wxList wxModalDialogs;
efb064f7 29
a15eb0a5 30IMPLEMENT_DYNAMIC_CLASS(wxDialog, wxTopLevelWindow)
e9576ca5 31
d491523b 32BEGIN_EVENT_TABLE(wxDialog, wxDialogBase)
e9576ca5
SC
33 EVT_BUTTON(wxID_OK, wxDialog::OnOK)
34 EVT_BUTTON(wxID_APPLY, wxDialog::OnApply)
35 EVT_BUTTON(wxID_CANCEL, wxDialog::OnCancel)
a15eb0a5 36
e9576ca5 37 EVT_CHAR_HOOK(wxDialog::OnCharHook)
a15eb0a5 38
e9576ca5 39 EVT_SYS_COLOUR_CHANGED(wxDialog::OnSysColourChanged)
a15eb0a5 40
e9576ca5
SC
41 EVT_CLOSE(wxDialog::OnCloseWindow)
42END_EVENT_TABLE()
43
efb064f7 44
2c326ada 45void wxDialog::Init()
e9576ca5 46{
2c326ada 47 m_isModalStyle = false;
e9576ca5
SC
48}
49
efb064f7
DS
50bool wxDialog::Create( wxWindow *parent,
51 wxWindowID id,
52 const wxString& title,
53 const wxPoint& pos,
54 const wxSize& size,
55 long style,
56 const wxString& name )
e9576ca5 57{
efb064f7 58 SetExtraStyle( GetExtraStyle() | wxTOPLEVEL_EX_DIALOG );
eeacbb8c 59
efb064f7 60 // All dialogs should really have this style...
facd6764 61 style |= wxTAB_TRAVERSAL;
eeacbb8c 62
efb064f7
DS
63 // ...but not these styles
64 style &= ~(wxYES | wxOK | wxNO); // | wxCANCEL
65
66 if ( !wxTopLevelWindow::Create( parent, id, title, pos, size, style, name ) )
1aa7b427 67 return false;
670f9935 68
cd17aeff 69#if TARGET_API_MAC_OSX
5e02e8e8 70 HIViewRef growBoxRef = 0 ;
efb064f7 71 OSStatus err = HIViewFindByID( HIViewGetRoot( (WindowRef)m_macWindow ), kHIViewWindowGrowBoxID, &growBoxRef );
5e02e8e8 72 if ( err == noErr && growBoxRef != 0 )
efb064f7 73 HIGrowBoxViewSetTransparent( growBoxRef, true ) ;
cd17aeff 74#endif
efb064f7 75
1aa7b427 76 return true;
e9576ca5
SC
77}
78
efb064f7 79void wxDialog::SetModal( bool flag )
e9576ca5 80{
e40298d5 81 if ( flag )
2f1ae414 82 {
2c326ada 83 m_isModalStyle = true;
eeacbb8c 84
efb064f7
DS
85 wxModelessWindows.DeleteObject( this );
86
643a0828 87#if TARGET_CARBON
efb064f7 88 SetWindowModality( (WindowRef)MacGetWindowRef(), kWindowModalityAppModal, NULL ) ;
643a0828 89#endif
2f1ae414
SC
90 }
91 else
92 {
2c326ada 93 m_isModalStyle = false;
eeacbb8c 94
efb064f7 95 wxModelessWindows.Append( this );
2f1ae414 96 }
e9576ca5
SC
97}
98
99wxDialog::~wxDialog()
100{
1aa7b427
DS
101 m_isBeingDeleted = true;
102 Show(false);
e9576ca5
SC
103}
104
90e572f1 105// By default, pressing escape cancels the dialog; on mac command-stop does the same thing
e9576ca5
SC
106void wxDialog::OnCharHook(wxKeyEvent& event)
107{
eeacbb8c 108 if (( event.m_keyCode == WXK_ESCAPE ||
e40298d5
JS
109 ( event.m_keyCode == '.' && event.MetaDown() ) )
110 && FindWindow(wxID_CANCEL) )
111 {
112 // Behaviour changed in 2.0: we'll send a Cancel message
113 // to the dialog instead of Close.
114 wxCommandEvent cancelEvent(wxEVT_COMMAND_BUTTON_CLICKED, wxID_CANCEL);
115 cancelEvent.SetEventObject( this );
116 GetEventHandler()->ProcessEvent(cancelEvent);
eeacbb8c 117
e40298d5
JS
118 return;
119 }
efb064f7 120
e40298d5
JS
121 // We didn't process this event.
122 event.Skip();
e9576ca5
SC
123}
124
2f1ae414 125bool wxDialog::IsModal() const
51abe921 126{
285ce5a3
JS
127 return wxModalDialogs.Find((wxDialog *)this) != NULL; // const_cast
128 // return m_isModalStyle;
51abe921
SC
129}
130
2f1ae414
SC
131
132bool wxDialog::IsModalShowing() const
51abe921 133{
2f1ae414 134 return wxModalDialogs.Find((wxDialog *)this) != NULL; // const_cast
51abe921
SC
135}
136
e9576ca5
SC
137bool wxDialog::Show(bool show)
138{
2f1ae414 139 if ( !wxDialogBase::Show(show) )
2f1ae414 140 // nothing to do
1aa7b427 141 return false;
e9576ca5 142
2f1ae414 143 if ( show )
2f1ae414
SC
144 // usually will result in TransferDataToWindow() being called
145 InitDialog();
e9576ca5 146
285ce5a3 147 if ( m_isModalStyle )
e7549107 148 {
2f1ae414
SC
149 if ( show )
150 {
151 DoShowModal();
152 }
153 else // end of modal dialog
154 {
1aa7b427 155 // this will cause IsModalShowing() return false and our local
2f1ae414
SC
156 // message loop will terminate
157 wxModalDialogs.DeleteObject(this);
158 }
159 }
e7549107 160
1aa7b427 161 return true;
e9576ca5
SC
162}
163
2726cac5
SC
164#if !TARGET_CARBON
165extern bool s_macIsInModalLoop ;
166#endif
167
2f1ae414 168void wxDialog::DoShowModal()
51abe921 169{
efb064f7 170 wxCHECK_RET( !IsModalShowing(), wxT("DoShowModal() called twice") );
51abe921 171
2f1ae414 172 wxModalDialogs.Append(this);
51abe921 173
90b78a56 174 SetFocus() ;
670f9935 175
2726cac5 176#if TARGET_CARBON
f697130e 177 BeginAppModalStateForWindow( (WindowRef) MacGetWindowRef()) ;
2726cac5 178#else
e40298d5
JS
179 // TODO : test whether parent gets disabled
180 bool formerModal = s_macIsInModalLoop ;
181 s_macIsInModalLoop = true ;
2726cac5 182#endif
efb064f7 183
e40298d5
JS
184 while ( IsModalShowing() )
185 {
186 wxTheApp->MacDoOneEvent() ;
187 // calls process idle itself
188 }
eeacbb8c 189
2726cac5 190#if TARGET_CARBON
f697130e 191 EndAppModalStateForWindow( (WindowRef) MacGetWindowRef() ) ;
2726cac5
SC
192#else
193 // TODO probably reenable the parent window if any
e40298d5 194 s_macIsInModalLoop = formerModal ;
2726cac5 195#endif
51abe921 196}
519cb848 197
2f1ae414 198
1aa7b427 199// Replacement for Show(true) for modal dialogs - returns return code
e9576ca5
SC
200int wxDialog::ShowModal()
201{
285ce5a3 202 if ( !m_isModalStyle )
1aa7b427 203 SetModal(true);
81b41c03 204
1aa7b427 205 Show(true);
efb064f7 206
e40298d5 207 return GetReturnCode();
e9576ca5
SC
208}
209
2f1ae414
SC
210// NB: this function (surprizingly) may be called for both modal and modeless
211// dialogs and should work for both of them
e9576ca5
SC
212void wxDialog::EndModal(int retCode)
213{
285ce5a3 214 SetReturnCode(retCode);
1aa7b427 215 Show(false);
285ce5a3 216 SetModal(false);
e9576ca5
SC
217}
218
219// Standard buttons
d208e641 220void wxDialog::OnOK(wxCommandEvent& WXUNUSED(event))
e9576ca5 221{
51abe921 222 if ( Validate() && TransferDataFromWindow() )
2f1ae414 223 EndModal(wxID_OK);
e9576ca5
SC
224}
225
d208e641 226void wxDialog::OnApply(wxCommandEvent& WXUNUSED(event))
e9576ca5 227{
51abe921 228 if (Validate())
1aa7b427
DS
229 TransferDataFromWindow();
230
51abe921 231 // TODO probably need to disable the Apply button until things change again
e9576ca5
SC
232}
233
d208e641 234void wxDialog::OnCancel(wxCommandEvent& WXUNUSED(event))
e9576ca5 235{
d208e641 236 EndModal(wxID_CANCEL);
7c74e7fe
SC
237}
238
d208e641 239void wxDialog::OnCloseWindow(wxCloseEvent& WXUNUSED(event))
e9576ca5 240{
e3065973 241 // We'll send a Cancel message by default,
e9576ca5 242 // which may close the dialog.
e3065973
JS
243 // Check for looping if the Cancel event handler calls Close().
244
245 // Note that if a cancel button and handler aren't present in the dialog,
246 // nothing will happen when you close the dialog via the window manager, or
247 // via Close().
248 // We wouldn't want to destroy the dialog by default, since the dialog may have been
249 // created on the stack.
250 // However, this does mean that calling dialog->Close() won't delete the dialog
251 // unless the handler for wxID_CANCEL does so. So use Destroy() if you want to be
252 // sure to destroy the dialog.
253 // The default OnCancel (above) simply ends a modal dialog, and hides a modeless dialog.
e9576ca5
SC
254
255 static wxList closing;
51abe921 256
e9576ca5 257 if ( closing.Member(this) )
e3065973 258 return;
51abe921 259
e9576ca5 260 closing.Append(this);
51abe921 261
e3065973
JS
262 wxCommandEvent cancelEvent(wxEVT_COMMAND_BUTTON_CLICKED, wxID_CANCEL);
263 cancelEvent.SetEventObject( this );
264 GetEventHandler()->ProcessEvent(cancelEvent); // This may close the dialog
e9576ca5
SC
265
266 closing.DeleteObject(this);
e9576ca5
SC
267}
268
d208e641 269void wxDialog::OnSysColourChanged(wxSysColourChangedEvent& WXUNUSED(event))
e9576ca5 270{
a756f210 271 SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_3DFACE));
e9576ca5
SC
272 Refresh();
273}