]> git.saurik.com Git - wxWidgets.git/blame - src/motif/msgdlg.cpp
Add wxEvtHandler::CallAfter() for asynchronous method calls.
[wxWidgets.git] / src / motif / msgdlg.cpp
CommitLineData
4bb6408c 1/////////////////////////////////////////////////////////////////////////////
e5b50758 2// Name: src/motif/msgdlg.cpp
4bb6408c
JS
3// Purpose: wxMessageDialog
4// Author: Julian Smart
5// Modified by:
6// Created: 04/01/98
e5b50758 7// RCS-ID: $Id$
4bb6408c 8// Copyright: (c) Julian Smart
65571936 9// Licence: wxWindows licence
4bb6408c
JS
10/////////////////////////////////////////////////////////////////////////////
11
ee31c392
VZ
12// ============================================================================
13// declarations
14// ============================================================================
15
ee31c392
VZ
16// ----------------------------------------------------------------------------
17// headers
18// ----------------------------------------------------------------------------
19
1248b41f
MB
20// For compilers that support precompilation, includes "wx.h".
21#include "wx/wxprec.h"
22
338dd992
JJ
23#ifdef __VMS
24#pragma message disable nosimpint
7ec69821 25#include "wx/vms_x_fix.h"
338dd992 26#endif
ee31c392
VZ
27#include <X11/Xlib.h>
28
29#include <Xm/Xm.h>
30#include <Xm/MessageB.h>
338dd992
JJ
31#ifdef __VMS
32#pragma message enable nosimpint
33#endif
ee31c392 34
eaa6f9ad 35#include "wx/msgdlg.h"
88a7a4e1
WS
36
37#ifndef WX_PRECOMP
38 #include "wx/intl.h"
670f9935 39 #include "wx/app.h"
9eddec69 40 #include "wx/settings.h"
88a7a4e1
WS
41#endif
42
ee31c392
VZ
43#include "wx/motif/private.h"
44
45// ----------------------------------------------------------------------------
46// macros
47// ----------------------------------------------------------------------------
4bb6408c 48
ee31c392 49 IMPLEMENT_CLASS(wxMessageDialog, wxDialog)
4bb6408c 50
ee31c392
VZ
51// ============================================================================
52// implementation
53// ============================================================================
54
55// ----------------------------------------------------------------------------
56// the callbacks for message box buttons
57// ----------------------------------------------------------------------------
58
59// the common part
ccebc98a 60static void msgboxCallBack(Widget w, void* client_data, int id)
ee31c392
VZ
61{
62 // close the dialog
63 XtUnmanageChild(w);
64
65 wxMessageDialog *dlg = (wxMessageDialog *)client_data;
66 dlg->SetResult(id);
67}
68
69static void msgboxCallBackOk(Widget w,
ccebc98a 70 void* client_data,
af111fc3 71 XmAnyCallbackStruct *WXUNUSED(call_data))
ee31c392
VZ
72{
73 msgboxCallBack(w, client_data, wxID_OK);
74}
75
76static void msgboxCallBackCancel(Widget w,
ccebc98a 77 void* client_data,
af111fc3 78 XmAnyCallbackStruct *WXUNUSED(call_data))
ee31c392
VZ
79{
80 msgboxCallBack(w, client_data, wxID_CANCEL);
81}
82
11d737b4 83static void msgboxCallBackHelp(Widget w,
ccebc98a 84 void* client_data,
af111fc3 85 XmAnyCallbackStruct *WXUNUSED(call_data))
11d737b4
MB
86{
87 msgboxCallBack(w, client_data, wxID_HELP);
88}
89
ee31c392 90static void msgboxCallBackClose(Widget w,
ccebc98a 91 void* client_data,
af111fc3 92 XmAnyCallbackStruct *WXUNUSED(call_data))
ee31c392
VZ
93{
94 msgboxCallBack(w, client_data, wxID_CANCEL);
95}
96
97// ----------------------------------------------------------------------------
98// wxMessageDialog
99// ----------------------------------------------------------------------------
100
ed05b5c6
VZ
101extern "C"
102{
103 typedef Widget (*DialogCreateFunction)(Widget, String, ArgList, Cardinal);
104}
105
4bb6408c
JS
106int wxMessageDialog::ShowModal()
107{
e5b50758
WS
108 const long style = GetMessageDialogStyle();
109
ed05b5c6 110 DialogCreateFunction dialogCreateFunction;
e5b50758 111 if ( style & wxYES_NO )
ee31c392
VZ
112 {
113 // if we have [Yes], it must be a question
114 dialogCreateFunction = XmCreateQuestionDialog;
ee31c392 115 }
e5b50758 116 else if ( style & wxICON_STOP )
ee31c392
VZ
117 {
118 // error dialog is the one with error icon...
119 dialogCreateFunction = XmCreateErrorDialog;
120 }
e5b50758 121 else if ( style & wxICON_EXCLAMATION )
ee31c392
VZ
122 {
123 // ...and the warning dialog too
124 dialogCreateFunction = XmCreateWarningDialog;
125 }
126 else
127 {
128 // finally, use the info dialog by default
129 dialogCreateFunction = XmCreateInformationDialog;
130 }
131
af111fc3 132 Widget wParent = m_parent ? GetWidget(m_parent) : (Widget) 0;
ee31c392
VZ
133 if ( !wParent )
134 {
135 wxWindow *window = wxTheApp->GetTopWindow();
136 if ( !window )
137 {
138 wxFAIL_MSG("can't show message box without parent window");
139
140 return wxID_CANCEL;
141 }
142
143 wParent = GetWidget(window);
144 }
145
ee1aaf99
JS
146 // prepare the arg list
147 Arg args[10];
148 int ac = 0;
149
2afb9e16 150 wxXmString text(GetFullMessage());
ee1aaf99
JS
151 wxXmString title(m_caption);
152 XtSetArg(args[ac], XmNmessageString, text()); ac++;
153 XtSetArg(args[ac], XmNdialogTitle, title()); ac++;
154
6ace5176
MB
155 Display* dpy = XtDisplay(wParent);
156
a1b806b9 157 if (m_backgroundColour.IsOk())
105fbe1f 158 {
d3b9f782 159 wxComputeColours (dpy, & m_backgroundColour, NULL);
ee1aaf99 160
105fbe1f
MB
161 XtSetArg(args[ac], XmNbackground, g_itemColors[wxBACK_INDEX].pixel); ac++;
162 XtSetArg(args[ac], XmNtopShadowColor, g_itemColors[wxTOPS_INDEX].pixel); ac++;
163 XtSetArg(args[ac], XmNbottomShadowColor, g_itemColors[wxBOTS_INDEX].pixel); ac++;
164 XtSetArg(args[ac], XmNforeground, g_itemColors[wxFORE_INDEX].pixel); ac++;
165 }
ee1aaf99 166
6ace5176
MB
167 wxFont font = wxSystemSettings::GetFont(wxSYS_DEFAULT_GUI_FONT);
168
7398fb81
MB
169#if __WXMOTIF20__ && !__WXLESSTIF__
170 XtSetArg(args[ac], XmNbuttonRenderTable, font.GetFontTypeC(dpy)); ac++;
171 XtSetArg(args[ac], XmNlabelRenderTable, font.GetFontTypeC(dpy)); ac++;
172 XtSetArg(args[ac], XmNtextRenderTable, font.GetFontTypeC(dpy)); ac++;
173#else
174 XtSetArg(args[ac], XmNbuttonFontList, font.GetFontTypeC(dpy)); ac++;
175 XtSetArg(args[ac], XmNlabelFontList, font.GetFontTypeC(dpy)); ac++;
176 XtSetArg(args[ac], XmNtextFontList, font.GetFontTypeC(dpy)); ac++;
177#endif
6ace5176 178
ee1aaf99
JS
179 // do create message box
180
da8cf723 181 Widget wMsgBox = (*dialogCreateFunction)(wParent, wxMOTIF_STR(""), args, ac);
ee31c392
VZ
182
183 wxCHECK_MSG( wMsgBox, wxID_CANCEL, "msg box creation failed" );
184
11d737b4
MB
185 // get the buttons which we might either remove or rename
186 // depending on the requested style
187 //
188 Widget wBtnOk = XmMessageBoxGetChild(wMsgBox, XmDIALOG_OK_BUTTON);
189 Widget wBtnHelp = XmMessageBoxGetChild(wMsgBox, XmDIALOG_HELP_BUTTON);
190 Widget wBtnCancel = XmMessageBoxGetChild(wMsgBox, XmDIALOG_CANCEL_BUTTON);
ee31c392 191
e5b50758 192 if ( style & wxYES_NO )
ee31c392 193 {
e5b50758 194 wxXmString yes(_("Yes")), no(_("No")), cancel(_("Cancel"));
ee31c392 195
e5b50758 196 if ( style & wxCANCEL )
ee31c392 197 {
11d737b4
MB
198 // use the cancel button for No and the help button for
199 // Cancel Yuk :-) MB
200 //
ee31c392
VZ
201 XtVaSetValues(wBtnOk, XmNlabelString, yes(), NULL);
202 XtVaSetValues(wBtnCancel, XmNlabelString, no(), NULL);
11d737b4 203 XtVaSetValues(wBtnHelp, XmNlabelString, cancel(), NULL);
ee31c392
VZ
204 }
205 else
206 {
11d737b4
MB
207 // no cancel button requested...
208 // remove the help button and use cancel for no
209 //
210 XtVaSetValues(wBtnCancel, XmNlabelString, no(), NULL);
211 XtUnmanageChild(wBtnHelp);
ee31c392
VZ
212 }
213 }
11d737b4
MB
214 else
215 {
216 // remove the help button and the cancel button (unless it was
217 // requested)
218 //
219 XtUnmanageChild(wBtnHelp);
e5b50758 220 if ( !(style & wxCANCEL ) ) XtUnmanageChild(wBtnCancel);
11d737b4 221 }
ee31c392
VZ
222
223 // set the callbacks for the message box buttons
224 XtAddCallback(wMsgBox, XmNokCallback,
225 (XtCallbackProc)msgboxCallBackOk, (XtPointer)this);
226 XtAddCallback(wMsgBox, XmNcancelCallback,
227 (XtCallbackProc)msgboxCallBackCancel, (XtPointer)this);
11d737b4
MB
228 XtAddCallback(wMsgBox, XmNhelpCallback,
229 (XtCallbackProc)msgboxCallBackHelp, (XtPointer)this);
ee31c392
VZ
230 XtAddCallback(wMsgBox, XmNunmapCallback,
231 (XtCallbackProc)msgboxCallBackClose, (XtPointer)this);
232
233 // show it as a modal dialog
234 XtManageChild(wMsgBox);
235 XtAddGrab(wMsgBox, True, False);
236
237 // the m_result will be changed when message box goes away
238 m_result = -1;
239
240 // local message loop
241 XtAppContext context = XtWidgetToApplicationContext(wParent);
242 XEvent event;
243 while ( m_result == -1 )
244 {
245 XtAppNextEvent(context, &event);
246 XtDispatchEvent(&event);
247 }
248
249 // translate the result if necessary
e5b50758 250 if ( style & wxYES_NO )
ee31c392
VZ
251 {
252 if ( m_result == wxID_OK )
253 m_result = wxID_YES;
254 else if ( m_result == wxID_CANCEL )
255 m_result = wxID_NO;
11d737b4
MB
256 else if ( m_result == wxID_HELP )
257 m_result = wxID_CANCEL;
ee31c392
VZ
258 }
259
260 return m_result;
4bb6408c 261}