1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/gtk/utilsgtk.cpp
4 // Author: Robert Roebling
6 // Copyright: (c) 1998 Robert Roebling
7 // Licence: wxWindows licence
8 /////////////////////////////////////////////////////////////////////////////
10 // For compilers that support precompilation, includes "wx.h".
11 #include "wx/wxprec.h"
16 #include "wx/string.h"
21 #include "wx/apptrait.h"
23 #include "wx/process.h"
25 #include "wx/unix/execute.h"
30 #include <sys/types.h>
31 #include <sys/wait.h> // for WNOHANG
39 #ifdef HAVE_X11_XKBLIB_H
40 /* under HP-UX and Solaris 2.6, at least, XKBlib.h defines structures with
41 * field named "explicit" - which is, of course, an error for a C++
42 * compiler. To be on the safe side, just redefine it everywhere. */
43 #define explicit __wx_explicit
45 #include "X11/XKBlib.h"
48 #endif // HAVE_X11_XKBLIB_H
53 #include "X11/SM/SMlib.h"
56 //-----------------------------------------------------------------------------
58 //-----------------------------------------------------------------------------
60 extern GtkWidget
*wxGetRootWindow();
62 //----------------------------------------------------------------------------
64 //----------------------------------------------------------------------------
66 // on OS/2, we use the wxBell from wxBase library
74 /* Don't synthesize KeyUp events holding down a key and producing
75 KeyDown events with autorepeat. */
76 #ifdef HAVE_X11_XKBLIB_H
77 bool wxSetDetectableAutoRepeat( bool flag
)
80 XkbSetDetectableAutoRepeat( GDK_DISPLAY(), flag
, &result
);
81 return result
; /* true if keyboard hardware supports this mode */
84 bool wxSetDetectableAutoRepeat( bool WXUNUSED(flag
) )
90 // Escapes string so that it is valid Pango markup XML string:
91 wxString
wxEscapeStringForPangoMarkup(const wxString
& str
)
93 size_t len
= str
.length();
96 for (size_t i
= 0; i
< len
; i
++)
125 // ----------------------------------------------------------------------------
126 // display characterstics
127 // ----------------------------------------------------------------------------
131 return GDK_DISPLAY();
134 void wxDisplaySize( int *width
, int *height
)
136 if (width
) *width
= gdk_screen_width();
137 if (height
) *height
= gdk_screen_height();
140 void wxDisplaySizeMM( int *width
, int *height
)
142 if (width
) *width
= gdk_screen_width_mm();
143 if (height
) *height
= gdk_screen_height_mm();
146 void wxClientDisplayRect(int *x
, int *y
, int *width
, int *height
)
148 // This is supposed to return desktop dimensions minus any window
149 // manager panels, menus, taskbars, etc. If there is a way to do that
150 // for this platform please fix this function, otherwise it defaults
151 // to the entire desktop.
154 wxDisplaySize(width
, height
);
157 void wxGetMousePosition( int* x
, int* y
)
159 gdk_window_get_pointer( (GdkWindow
*) NULL
, x
, y
, (GdkModifierType
*) NULL
);
162 bool wxColourDisplay()
169 return gdk_drawable_get_visual( wxGetRootWindow()->window
)->depth
;
172 wxWindow
* wxFindWindowAtPoint(const wxPoint
& pt
)
174 return wxGenericFindWindowAtPoint(pt
);
179 wxCharBuffer
wxConvertToGTK(const wxString
& s
, wxFontEncoding enc
)
182 if ( enc
== wxFONTENCODING_UTF8
)
184 // no need for conversion at all, but do check that we have a valid
185 // UTF-8 string because passing invalid UTF-8 to GTK+ is going to
186 // result in a GTK+ error message and, especially, loss of data which
187 // was supposed to be shown in the GUI
188 if ( wxConvUTF8
.ToWChar(NULL
, 0, s
, s
.length()) == wxCONV_FAILED
)
190 // warn the programmer that something is probably wrong in his code
192 // NB: don't include the string in output because chances are that
193 // this invalid UTF-8 string could result in more errors itself
194 // if the application shows logs in the GUI and so we get into
196 wxLogDebug(_T("Invalid UTF-8 string in wxConvertToGTK()"));
198 // but still try to show at least something on the screen
199 wxMBConvUTF8
utf8permissive(wxMBConvUTF8::MAP_INVALID_UTF8_TO_OCTAL
);
200 wxWCharBuffer
wbuf(utf8permissive
.cMB2WC(s
));
201 buf
= wxConvUTF8
.cWC2MB(wbuf
);
203 else // valid UTF-8 string, no need to convert
205 buf
= wxCharBuffer(s
);
211 if ( enc
== wxFONTENCODING_SYSTEM
|| enc
== wxFONTENCODING_DEFAULT
)
213 wbuf
= wxConvUI
->cMB2WC(s
);
215 else // another encoding, use generic conversion class
217 wbuf
= wxCSConv(enc
).cMB2WC(s
);
221 buf
= wxConvUTF8
.cWC2MB(wbuf
);
227 #endif // !wxUSE_UNICODE
229 // ----------------------------------------------------------------------------
230 // subprocess routines
231 // ----------------------------------------------------------------------------
235 void GTK_EndProcessDetector(gpointer data
, gint source
,
236 GdkInputCondition
WXUNUSED(condition
) )
238 wxEndProcessData
*proc_data
= (wxEndProcessData
*)data
;
240 // has the process really terminated? unfortunately GDK (or GLib) seem to
241 // generate G_IO_HUP notification even when it simply tries to read from a
242 // closed fd and hasn't terminated at all
243 int pid
= (proc_data
->pid
> 0) ? proc_data
->pid
: -(proc_data
->pid
);
245 int rc
= waitpid(pid
, &status
, WNOHANG
);
249 // no, it didn't exit yet, continue waiting
253 // set exit code to -1 if something bad happened
254 proc_data
->exitcode
= rc
!= -1 && WIFEXITED(status
) ? WEXITSTATUS(status
)
257 // child exited, end waiting
260 // don't call us again!
261 gdk_input_remove(proc_data
->tag
);
263 wxHandleProcessTermination(proc_data
);
267 int wxAddProcessCallback(wxEndProcessData
*proc_data
, int fd
)
269 int tag
= gdk_input_add(fd
,
271 GTK_EndProcessDetector
,
272 (gpointer
)proc_data
);
279 // ----------------------------------------------------------------------------
280 // wxPlatformInfo-related
281 // ----------------------------------------------------------------------------
283 wxPortId
wxGUIAppTraits::GetToolkitVersion(int *verMaj
, int *verMin
) const
286 *verMaj
= gtk_major_version
;
288 *verMin
= gtk_minor_version
;
294 static wxString
GetSM()
300 dpy
= XOpenDisplay(NULL
);
302 smc_conn
= SmcOpenConnection(NULL
, NULL
,
304 0 /* mask */, NULL
/* callbacks */,
305 NULL
, &client_id_ret
, 0, NULL
);
307 vendor
= SmcVendor(smc_conn
);
308 wxString ret
= wxString::FromAscii( vendor
);
311 SmcCloseConnection(smc_conn
, 0, NULL
);
320 wxString
wxGUIAppTraits::GetDesktopEnvironment() const
323 wxString SM
= GetSM();
325 if (SM
== wxT("GnomeSM"))
328 if (SM
== wxT("KDE"))
332 return wxEmptyString
;