1 /////////////////////////////////////////////////////////////////////////////
4 // Author: Robert Roebling
6 // Copyright: (c) 1998 Robert Roebling, Julian Smart
7 // Licence: wxWindows licence
8 /////////////////////////////////////////////////////////////////////////////
12 #pragma implementation "window.h"
16 #include "wx/window.h"
20 #include "wx/layout.h"
22 #include "wx/dialog.h"
23 #include "wx/msgdlg.h"
25 #if wxUSE_DRAG_AND_DROP
30 #include "wx/tooltip.h"
34 #include "wx/statusbr.h"
36 #include "wx/settings.h"
43 #include "gdk/gdkprivate.h"
44 #include "gdk/gdkkeysyms.h"
45 #include "wx/gtk/win_gtk.h"
47 //-----------------------------------------------------------------------------
48 // documentation on internals
49 //-----------------------------------------------------------------------------
52 I have been asked several times about writing some documentation about
53 the GTK port of wxWindows, especially its internal structures. Obviously,
54 you cannot understand wxGTK without knowing a little about the GTK, but
55 some more information about what the wxWindow, which is the base class
56 for all other window classes, does seems required as well.
58 What does wxWindow do? It contains the common interface for the following
59 jobs of its descendants:
61 1) Define the rudimentary behaviour common to all window classes, such as
62 resizing, intercepting user input (so as to make it possible to use these
63 events for special purposes in a derived class), window names etc.
65 2) Provide the possibility to contain and manage children, if the derived
66 class is allowed to contain children, which holds true for those window
67 classes which do not display a native GTK widget. To name them, these
68 classes are wxPanel, wxScrolledWindow, wxDialog, wxFrame. The MDI frame-
69 work classes are a special case and are handled a bit differently from
70 the rest. The same holds true for the wxNotebook class.
72 3) Provide the possibility to draw into a client area of a window. This,
73 too, only holds true for classes that do not display a native GTK widget
76 4) Provide the entire mechanism for scrolling widgets. This actual inter-
77 face for this is usually in wxScrolledWindow, but the GTK implementation
80 5) A multitude of helper or extra methods for special purposes, such as
81 Drag'n'Drop, managing validators etc.
83 Normally one might expect, that one wxWindows window would always correspond
84 to one GTK widget. Under GTK, there is no such allround widget that has all
85 the functionality. Moreover, the GTK defines a client area as a different
86 widget from the actual widget you are handling. Last but not least some
87 special classes (e.g. wxFrame) handle different categories of widgets and
88 still have the possibility to draw something in the client area.
89 It was therefore required to write a special purpose GTK widget, that would
90 represent a client area in the sense of wxWindows capable to do the jobs
91 2), 3) and 4). I have written this class and it resides in win_gtk.c of
94 All windows must have a widget, with which they interact with other under-
95 lying GTK widgets. It is this widget, e.g. that has to be resized etc and
96 thw wxWindow class has a member variable called m_widget which holds a
97 pointer to this widget. When the window class represents a GTK native widget,
98 this is (in most cases) the only GTK widget the class manages. E.g. the
99 wxStatitText class handles only a GtkLabel widget a pointer to which you
100 can find in m_widget (defined in wxWindow)
102 When the class has a client area for drawing into and for containing children
103 it has to handle the client area widget (of the type GtkMyFixed, defined in
104 win_gtk.c), but there could be any number of widgets, handled by a class
105 The common rule for all windows is only, that the widget that interacts with
106 the rest of GTK must be referenced in m_widget and all other widgets must be
107 children of this widget on the GTK level. The top-most widget, which also
108 represents the client area, must be in the m_wxwindow field and must be of
111 As I said, the window classes that display a GTK native widget only have
112 one widget, so in the case of e.g. the wxButton class m_widget holds a
113 pointer to a GtkButton widget. But windows with client areas (for drawing
114 and children) have a m_widget field that is a pointer to a GtkScrolled-
115 Window and a m_wxwindow field that is pointer to a GtkMyFixed and this
116 one is (in the GTK sense) a child of the GtkScrolledWindow.
118 If the m_wxwindow field is set, then all input to this widget is inter-
119 cepted and sent to the wxWindows class. If not, all input to the widget
120 that gets pointed to by m_widget gets intercepted and sent to the class.
124 //-----------------------------------------------------------------------------
126 //-----------------------------------------------------------------------------
128 extern wxList wxPendingDelete
;
129 extern bool g_blockEventsOnDrag
;
130 extern bool g_blockEventsOnScroll
;
131 extern bool g_isIdle
;
132 static bool g_capturing
= FALSE
;
133 static wxWindow
*g_focusWindow
= (wxWindow
*) NULL
;
135 /* hack: we need something to pass to gtk_menu_popup, so we store the time of
136 the last click here */
137 static guint32 gs_timeLastClick
= 0;
139 //-----------------------------------------------------------------------------
141 //-----------------------------------------------------------------------------
143 extern void wxapp_install_idle_handler();
144 extern bool g_isIdle
;
146 #if (GTK_MINOR_VERSION > 0)
148 //-----------------------------------------------------------------------------
149 // local code (see below)
150 //-----------------------------------------------------------------------------
152 static void draw_frame( GtkWidget
*widget
, wxWindow
*win
)
154 if (!win
->HasVMT()) return;
159 if (win
->m_hasScrolling
)
161 GtkScrolledWindow
*scroll_window
= GTK_SCROLLED_WINDOW(widget
);
162 GtkScrolledWindowClass
*scroll_class
= GTK_SCROLLED_WINDOW_CLASS( GTK_OBJECT(widget
)->klass
);
165 GtkWidget *hscrollbar = scroll_window->hscrollbar;
166 GtkWidget *vscrollbar = scroll_window->vscrollbar;
168 we use this instead: range.slider_width = 11 + 2*2pts edge
171 if (scroll_window
->vscrollbar_visible
)
173 dw
+= 15; /* dw += vscrollbar->allocation.width; */
174 dw
+= scroll_class
->scrollbar_spacing
;
177 if (scroll_window
->hscrollbar_visible
)
179 dh
+= 15; /* dh += hscrollbar->allocation.height; */
180 dw
+= scroll_class
->scrollbar_spacing
;
186 if (GTK_WIDGET_NO_WINDOW (widget
))
188 dx
+= widget
->allocation
.x
;
189 dy
+= widget
->allocation
.y
;
192 if (win
->m_windowStyle
& wxRAISED_BORDER
)
194 gtk_draw_shadow( widget
->style
,
199 win
->m_width
-dw
, win
->m_height
-dh
);
203 if (win
->m_windowStyle
& wxSUNKEN_BORDER
)
205 gtk_draw_shadow( widget
->style
,
210 win
->m_width
-dw
, win
->m_height
-dh
);
215 //-----------------------------------------------------------------------------
216 // "expose_event" of m_widget
217 //-----------------------------------------------------------------------------
219 static void gtk_window_own_expose_callback( GtkWidget
*widget
, GdkEventExpose
*gdk_event
, wxWindow
*win
)
221 if (gdk_event
->count
> 0) return;
222 draw_frame( widget
, win
);
225 //-----------------------------------------------------------------------------
226 // "draw" of m_wxwindow
227 //-----------------------------------------------------------------------------
229 static void gtk_window_own_draw_callback( GtkWidget
*widget
, GdkRectangle
*WXUNUSED(rect
), wxWindow
*win
)
231 draw_frame( widget
, win
);
236 //-----------------------------------------------------------------------------
237 // "expose_event" of m_wxwindow
238 //-----------------------------------------------------------------------------
240 static void gtk_window_expose_callback( GtkWidget
*WXUNUSED(widget
), GdkEventExpose
*gdk_event
, wxWindow
*win
)
242 if (g_isIdle
) wxapp_install_idle_handler();
244 if (!win
->HasVMT()) return;
246 win
->m_updateRegion
.Union( gdk_event
->area
.x
,
248 gdk_event
->area
.width
,
249 gdk_event
->area
.height
);
251 if (gdk_event
->count
> 0) return;
254 printf( "OnExpose from " );
255 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
256 printf( win->GetClassInfo()->GetClassName() );
260 wxPaintEvent
event( win
->GetId() );
261 event
.SetEventObject( win
);
262 win
->GetEventHandler()->ProcessEvent( event
);
264 win
->m_updateRegion
.Clear();
267 //-----------------------------------------------------------------------------
268 // "draw" of m_wxwindow
269 //-----------------------------------------------------------------------------
271 static void gtk_window_draw_callback( GtkWidget
*WXUNUSED(widget
), GdkRectangle
*rect
, wxWindow
*win
)
273 if (g_isIdle
) wxapp_install_idle_handler();
275 if (!win
->HasVMT()) return;
277 win
->m_updateRegion
.Union( rect
->x
, rect
->y
, rect
->width
, rect
->height
);
279 wxPaintEvent
event( win
->GetId() );
280 event
.SetEventObject( win
);
281 win
->GetEventHandler()->ProcessEvent( event
);
283 win
->m_updateRegion
.Clear();
286 //-----------------------------------------------------------------------------
287 // "key_press_event" from any window
288 //-----------------------------------------------------------------------------
290 static gint
gtk_window_key_press_callback( GtkWidget
*widget
, GdkEventKey
*gdk_event
, wxWindow
*win
)
292 if (g_isIdle
) wxapp_install_idle_handler();
294 if (!win
->HasVMT()) return FALSE
;
295 if (g_blockEventsOnDrag
) return FALSE
;
298 wxPrintf( _T("OnKeyPress from ") );
299 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
300 wxPrintf( win->GetClassInfo()->GetClassName() );
301 wxPrintf( _T(".\n") );
305 switch (gdk_event
->keyval
)
307 case GDK_BackSpace
: key_code
= WXK_BACK
; break;
308 case GDK_ISO_Left_Tab
:
310 case GDK_Tab
: key_code
= WXK_TAB
; break;
311 case GDK_Linefeed
: key_code
= WXK_RETURN
; break;
312 case GDK_Clear
: key_code
= WXK_CLEAR
; break;
313 case GDK_Return
: key_code
= WXK_RETURN
; break;
314 case GDK_Pause
: key_code
= WXK_PAUSE
; break;
315 case GDK_Scroll_Lock
: key_code
= WXK_SCROLL
; break;
316 case GDK_Escape
: key_code
= WXK_ESCAPE
; break;
317 case GDK_Delete
: key_code
= WXK_DELETE
; break;
318 case GDK_Home
: key_code
= WXK_HOME
; break;
319 case GDK_Left
: key_code
= WXK_LEFT
; break;
320 case GDK_Up
: key_code
= WXK_UP
; break;
321 case GDK_Right
: key_code
= WXK_RIGHT
; break;
322 case GDK_Down
: key_code
= WXK_DOWN
; break;
323 case GDK_Prior
: key_code
= WXK_PRIOR
; break;
324 // case GDK_Page_Up: key_code = WXK_PAGEUP; break;
325 case GDK_Next
: key_code
= WXK_NEXT
; break;
326 // case GDK_Page_Down: key_code = WXK_PAGEDOWN; break;
327 case GDK_End
: key_code
= WXK_END
; break;
328 case GDK_Begin
: key_code
= WXK_HOME
; break;
329 case GDK_Select
: key_code
= WXK_SELECT
; break;
330 case GDK_Print
: key_code
= WXK_PRINT
; break;
331 case GDK_Execute
: key_code
= WXK_EXECUTE
; break;
332 case GDK_Insert
: key_code
= WXK_INSERT
; break;
333 case GDK_Num_Lock
: key_code
= WXK_NUMLOCK
; break;
334 case GDK_KP_Enter
: key_code
= WXK_RETURN
; break;
335 case GDK_KP_Home
: key_code
= WXK_HOME
; break;
336 case GDK_KP_Left
: key_code
= WXK_LEFT
; break;
337 case GDK_KP_Up
: key_code
= WXK_UP
; break;
338 case GDK_KP_Right
: key_code
= WXK_RIGHT
; break;
339 case GDK_KP_Down
: key_code
= WXK_DOWN
; break;
340 case GDK_KP_Prior
: key_code
= WXK_PRIOR
; break;
341 // case GDK_KP_Page_Up: key_code = WXK_PAGEUP; break;
342 case GDK_KP_Next
: key_code
= WXK_NEXT
; break;
343 // case GDK_KP_Page_Down: key_code = WXK_PAGEDOWN; break;
344 case GDK_KP_End
: key_code
= WXK_END
; break;
345 case GDK_KP_Begin
: key_code
= WXK_HOME
; break;
346 case GDK_KP_Insert
: key_code
= WXK_INSERT
; break;
347 case GDK_KP_Delete
: key_code
= WXK_DELETE
; break;
348 case GDK_KP_Multiply
: key_code
= WXK_MULTIPLY
; break;
349 case GDK_KP_Add
: key_code
= WXK_ADD
; break;
350 case GDK_KP_Separator
: key_code
= WXK_SEPARATOR
; break;
351 case GDK_KP_Subtract
: key_code
= WXK_SUBTRACT
; break;
352 case GDK_KP_Decimal
: key_code
= WXK_DECIMAL
; break;
353 case GDK_KP_Divide
: key_code
= WXK_DIVIDE
; break;
354 case GDK_KP_0
: key_code
= WXK_NUMPAD0
; break;
355 case GDK_KP_1
: key_code
= WXK_NUMPAD1
; break;
356 case GDK_KP_2
: key_code
= WXK_NUMPAD2
; break;
357 case GDK_KP_3
: key_code
= WXK_NUMPAD3
; break;
358 case GDK_KP_4
: key_code
= WXK_NUMPAD4
; break;
359 case GDK_KP_5
: key_code
= WXK_NUMPAD5
; break;
360 case GDK_KP_6
: key_code
= WXK_NUMPAD6
; break;
361 case GDK_KP_7
: key_code
= WXK_NUMPAD7
; break;
362 case GDK_KP_8
: key_code
= WXK_NUMPAD7
; break;
363 case GDK_KP_9
: key_code
= WXK_NUMPAD9
; break;
364 case GDK_F1
: key_code
= WXK_F1
; break;
365 case GDK_F2
: key_code
= WXK_F2
; break;
366 case GDK_F3
: key_code
= WXK_F3
; break;
367 case GDK_F4
: key_code
= WXK_F4
; break;
368 case GDK_F5
: key_code
= WXK_F5
; break;
369 case GDK_F6
: key_code
= WXK_F6
; break;
370 case GDK_F7
: key_code
= WXK_F7
; break;
371 case GDK_F8
: key_code
= WXK_F8
; break;
372 case GDK_F9
: key_code
= WXK_F9
; break;
373 case GDK_F10
: key_code
= WXK_F10
; break;
374 case GDK_F11
: key_code
= WXK_F11
; break;
375 case GDK_F12
: key_code
= WXK_F12
; break;
378 if ((gdk_event
->keyval
>= 0x20) && (gdk_event
->keyval
<= 0xFF))
379 key_code
= gdk_event
->keyval
;
383 if (!key_code
) return FALSE
;
385 wxKeyEvent
event( wxEVT_KEY_DOWN
);
386 event
.m_shiftDown
= (gdk_event
->state
& GDK_SHIFT_MASK
);
387 event
.m_controlDown
= (gdk_event
->state
& GDK_CONTROL_MASK
);
388 event
.m_altDown
= (gdk_event
->state
& GDK_MOD1_MASK
);
389 event
.m_metaDown
= (gdk_event
->state
& GDK_MOD2_MASK
);
390 event
.m_keyCode
= key_code
;
393 event
.SetEventObject( win
);
395 bool ret
= win
->GetEventHandler()->ProcessEvent( event
);
399 wxWindow
*ancestor
= win
;
402 int command
= ancestor
->GetAcceleratorTable()->GetCommand( event
);
405 wxCommandEvent
command_event( wxEVT_COMMAND_MENU_SELECTED
, command
);
406 ret
= ancestor
->GetEventHandler()->ProcessEvent( command_event
);
409 ancestor
= ancestor
->GetParent();
413 // win is a control: tab can be propagated up
415 ((gdk_event
->keyval
== GDK_Tab
) || (gdk_event
->keyval
== GDK_ISO_Left_Tab
)) &&
416 ((win
->m_windowStyle
& wxTE_PROCESS_TAB
) == 0))
418 wxNavigationKeyEvent new_event
;
419 /* GDK reports GDK_ISO_Left_Tab for SHIFT-TAB */
420 new_event
.SetDirection( (gdk_event
->keyval
== GDK_Tab
) );
421 /* CTRL-TAB changes the (parent) window, i.e. switch notebook page */
422 new_event
.SetWindowChange( (gdk_event
->state
& GDK_CONTROL_MASK
) );
423 new_event
.SetCurrentFocus( win
);
424 ret
= win
->GetEventHandler()->ProcessEvent( new_event
);
428 (gdk_event
->keyval
== GDK_Escape
) )
430 wxCommandEvent
new_event(wxEVT_COMMAND_BUTTON_CLICKED
,wxID_CANCEL
);
431 new_event
.SetEventObject( win
);
432 ret
= win
->GetEventHandler()->ProcessEvent( new_event
);
436 Damn, I forgot why this didn't work, but it didn't work.
438 // win is a panel: up can be propagated to the panel
439 if ((!ret) && (win->m_wxwindow) && (win->m_parent) && (win->m_parent->AcceptsFocus()) &&
440 (gdk_event->keyval == GDK_Up))
442 win->m_parent->SetFocus();
446 // win is a panel: left/right can be propagated to the panel
447 if ((!ret) && (win->m_wxwindow) &&
448 ((gdk_event->keyval == GDK_Right) || (gdk_event->keyval == GDK_Left) ||
449 (gdk_event->keyval == GDK_Up) || (gdk_event->keyval == GDK_Down)))
451 wxNavigationKeyEvent new_event;
452 new_event.SetDirection( (gdk_event->keyval == GDK_Right) || (gdk_event->keyval == GDK_Down) );
453 new_event.SetCurrentFocus( win );
454 ret = win->GetEventHandler()->ProcessEvent( new_event );
460 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "key_press_event" );
467 //-----------------------------------------------------------------------------
468 // "key_release_event" from any window
469 //-----------------------------------------------------------------------------
471 static gint
gtk_window_key_release_callback( GtkWidget
*widget
, GdkEventKey
*gdk_event
, wxWindow
*win
)
473 if (g_isIdle
) wxapp_install_idle_handler();
475 if (!win
->HasVMT()) return FALSE
;
476 if (g_blockEventsOnDrag
) return FALSE
;
479 printf( "OnKeyRelease from " );
480 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
481 printf( win->GetClassInfo()->GetClassName() );
486 switch (gdk_event
->keyval
)
488 case GDK_BackSpace
: key_code
= WXK_BACK
; break;
489 case GDK_ISO_Left_Tab
:
491 case GDK_Tab
: key_code
= WXK_TAB
; break;
492 case GDK_Linefeed
: key_code
= WXK_RETURN
; break;
493 case GDK_Clear
: key_code
= WXK_CLEAR
; break;
494 case GDK_Return
: key_code
= WXK_RETURN
; break;
495 case GDK_Pause
: key_code
= WXK_PAUSE
; break;
496 case GDK_Scroll_Lock
: key_code
= WXK_SCROLL
; break;
497 case GDK_Escape
: key_code
= WXK_ESCAPE
; break;
498 case GDK_Delete
: key_code
= WXK_DELETE
; break;
499 case GDK_Home
: key_code
= WXK_HOME
; break;
500 case GDK_Left
: key_code
= WXK_LEFT
; break;
501 case GDK_Up
: key_code
= WXK_UP
; break;
502 case GDK_Right
: key_code
= WXK_RIGHT
; break;
503 case GDK_Down
: key_code
= WXK_DOWN
; break;
504 case GDK_Prior
: key_code
= WXK_PRIOR
; break;
505 // case GDK_Page_Up: key_code = WXK_PAGEUP; break;
506 case GDK_Next
: key_code
= WXK_NEXT
; break;
507 // case GDK_Page_Down: key_code = WXK_PAGEDOWN; break;
508 case GDK_End
: key_code
= WXK_END
; break;
509 case GDK_Begin
: key_code
= WXK_HOME
; break;
510 case GDK_Select
: key_code
= WXK_SELECT
; break;
511 case GDK_Print
: key_code
= WXK_PRINT
; break;
512 case GDK_Execute
: key_code
= WXK_EXECUTE
; break;
513 case GDK_Insert
: key_code
= WXK_INSERT
; break;
514 case GDK_Num_Lock
: key_code
= WXK_NUMLOCK
; break;
515 case GDK_KP_Enter
: key_code
= WXK_RETURN
; break;
516 case GDK_KP_Home
: key_code
= WXK_HOME
; break;
517 case GDK_KP_Left
: key_code
= WXK_LEFT
; break;
518 case GDK_KP_Up
: key_code
= WXK_UP
; break;
519 case GDK_KP_Right
: key_code
= WXK_RIGHT
; break;
520 case GDK_KP_Down
: key_code
= WXK_DOWN
; break;
521 case GDK_KP_Prior
: key_code
= WXK_PRIOR
; break;
522 // case GDK_KP_Page_Up: key_code = WXK_PAGEUP; break;
523 case GDK_KP_Next
: key_code
= WXK_NEXT
; break;
524 // case GDK_KP_Page_Down: key_code = WXK_PAGEDOWN; break;
525 case GDK_KP_End
: key_code
= WXK_END
; break;
526 case GDK_KP_Begin
: key_code
= WXK_HOME
; break;
527 case GDK_KP_Insert
: key_code
= WXK_INSERT
; break;
528 case GDK_KP_Delete
: key_code
= WXK_DELETE
; break;
529 case GDK_KP_Multiply
: key_code
= WXK_MULTIPLY
; break;
530 case GDK_KP_Add
: key_code
= WXK_ADD
; break;
531 case GDK_KP_Separator
: key_code
= WXK_SEPARATOR
; break;
532 case GDK_KP_Subtract
: key_code
= WXK_SUBTRACT
; break;
533 case GDK_KP_Decimal
: key_code
= WXK_DECIMAL
; break;
534 case GDK_KP_Divide
: key_code
= WXK_DIVIDE
; break;
535 case GDK_KP_0
: key_code
= WXK_NUMPAD0
; break;
536 case GDK_KP_1
: key_code
= WXK_NUMPAD1
; break;
537 case GDK_KP_2
: key_code
= WXK_NUMPAD2
; break;
538 case GDK_KP_3
: key_code
= WXK_NUMPAD3
; break;
539 case GDK_KP_4
: key_code
= WXK_NUMPAD4
; break;
540 case GDK_KP_5
: key_code
= WXK_NUMPAD5
; break;
541 case GDK_KP_6
: key_code
= WXK_NUMPAD6
; break;
542 case GDK_KP_7
: key_code
= WXK_NUMPAD7
; break;
543 case GDK_KP_8
: key_code
= WXK_NUMPAD7
; break;
544 case GDK_KP_9
: key_code
= WXK_NUMPAD9
; break;
545 case GDK_F1
: key_code
= WXK_F1
; break;
546 case GDK_F2
: key_code
= WXK_F2
; break;
547 case GDK_F3
: key_code
= WXK_F3
; break;
548 case GDK_F4
: key_code
= WXK_F4
; break;
549 case GDK_F5
: key_code
= WXK_F5
; break;
550 case GDK_F6
: key_code
= WXK_F6
; break;
551 case GDK_F7
: key_code
= WXK_F7
; break;
552 case GDK_F8
: key_code
= WXK_F8
; break;
553 case GDK_F9
: key_code
= WXK_F9
; break;
554 case GDK_F10
: key_code
= WXK_F10
; break;
555 case GDK_F11
: key_code
= WXK_F11
; break;
556 case GDK_F12
: key_code
= WXK_F12
; break;
559 if ((gdk_event
->keyval
>= 0x20) && (gdk_event
->keyval
<= 0xFF))
560 key_code
= gdk_event
->keyval
;
564 if (!key_code
) return FALSE
;
566 wxKeyEvent
event( wxEVT_KEY_UP
);
567 event
.m_shiftDown
= (gdk_event
->state
& GDK_SHIFT_MASK
);
568 event
.m_controlDown
= (gdk_event
->state
& GDK_CONTROL_MASK
);
569 event
.m_altDown
= (gdk_event
->state
& GDK_MOD1_MASK
);
570 event
.m_metaDown
= (gdk_event
->state
& GDK_MOD2_MASK
);
571 event
.m_keyCode
= key_code
;
574 event
.SetEventObject( win
);
576 if (win
->GetEventHandler()->ProcessEvent( event
))
578 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "key_release_event" );
585 //-----------------------------------------------------------------------------
586 // "button_press_event"
587 //-----------------------------------------------------------------------------
589 static gint
gtk_window_button_press_callback( GtkWidget
*widget
, GdkEventButton
*gdk_event
, wxWindow
*win
)
591 if (g_isIdle
) wxapp_install_idle_handler();
594 wxPrintf( _T("1) OnButtonPress from ") );
595 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
596 wxPrintf( win->GetClassInfo()->GetClassName() );
597 wxPrintf( _T(".\n") );
600 if (!win
->HasVMT()) return FALSE
;
601 if (g_blockEventsOnDrag
) return TRUE
;
602 if (g_blockEventsOnScroll
) return TRUE
;
604 if (!win
->IsOwnGtkWindow( gdk_event
->window
)) return FALSE
;
608 if (GTK_WIDGET_CAN_FOCUS(win
->m_wxwindow
) && !GTK_WIDGET_HAS_FOCUS (win
->m_wxwindow
) )
610 gtk_widget_grab_focus (win
->m_wxwindow
);
613 wxPrintf( _T("GrabFocus from ") );
614 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
615 wxPrintf( win->GetClassInfo()->GetClassName() );
616 wxPrintf( _T(".\n") );
623 wxPrintf( _T("No GrabFocus from ") );
624 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
625 wxPrintf( win->GetClassInfo()->GetClassName() );
626 if (GTK_WIDGET_CAN_FOCUS(win->m_wxwindow))
627 wxPrintf( _T(" because it already has") );
628 wxPrintf( _T(".\n") );
634 wxPrintf( _T("2) OnButtonPress from ") );
635 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
636 wxPrintf( win->GetClassInfo()->GetClassName() );
637 wxPrintf( _T(".\n") );
640 wxEventType event_type
= wxEVT_LEFT_DOWN
;
642 if (gdk_event
->button
== 1)
644 switch (gdk_event
->type
)
646 case GDK_BUTTON_PRESS
: event_type
= wxEVT_LEFT_DOWN
; break;
647 case GDK_2BUTTON_PRESS
: event_type
= wxEVT_LEFT_DCLICK
; break;
651 else if (gdk_event
->button
== 2)
653 switch (gdk_event
->type
)
655 case GDK_BUTTON_PRESS
: event_type
= wxEVT_MIDDLE_DOWN
; break;
656 case GDK_2BUTTON_PRESS
: event_type
= wxEVT_MIDDLE_DCLICK
; break;
660 else if (gdk_event
->button
== 3)
662 switch (gdk_event
->type
)
664 case GDK_BUTTON_PRESS
: event_type
= wxEVT_RIGHT_DOWN
; break;
665 case GDK_2BUTTON_PRESS
: event_type
= wxEVT_RIGHT_DCLICK
; break;
670 wxMouseEvent
event( event_type
);
671 event
.m_shiftDown
= (gdk_event
->state
& GDK_SHIFT_MASK
);
672 event
.m_controlDown
= (gdk_event
->state
& GDK_CONTROL_MASK
);
673 event
.m_altDown
= (gdk_event
->state
& GDK_MOD1_MASK
);
674 event
.m_metaDown
= (gdk_event
->state
& GDK_MOD2_MASK
);
675 event
.m_leftDown
= (gdk_event
->state
& GDK_BUTTON1_MASK
);
676 event
.m_middleDown
= (gdk_event
->state
& GDK_BUTTON2_MASK
);
677 event
.m_rightDown
= (gdk_event
->state
& GDK_BUTTON3_MASK
);
679 event
.m_x
= (long)gdk_event
->x
;
680 event
.m_y
= (long)gdk_event
->y
;
682 // Some control don't have their own X window and thus cannot get
687 wxNode
*node
= win
->GetChildren().First();
690 wxWindow
*child
= (wxWindow
*)node
->Data();
692 if (child
->m_isStaticBox
)
694 // wxStaticBox is transparent in the box itself
697 int xx1
= child
->m_x
;
698 int yy1
= child
->m_y
;
699 int xx2
= child
->m_x
+ child
->m_width
;
700 int yy2
= child
->m_x
+ child
->m_height
;
703 if (((x
>= xx1
) && (x
<= xx1
+10) && (y
>= yy1
) && (y
<= yy2
)) ||
705 ((x
>= xx2
-10) && (x
<= xx2
) && (y
>= yy1
) && (y
<= yy2
)) ||
707 ((x
>= xx1
) && (x
<= xx2
) && (y
>= yy1
) && (y
<= yy1
+10)) ||
709 ((x
>= xx1
) && (x
<= xx2
) && (y
>= yy2
-1) && (y
<= yy2
)))
712 event
.m_x
-= child
->m_x
;
713 event
.m_y
-= child
->m_y
;
720 if ((child
->m_wxwindow
== (GtkWidget
*) NULL
) &&
721 (child
->m_x
<= event
.m_x
) &&
722 (child
->m_y
<= event
.m_y
) &&
723 (child
->m_x
+child
->m_width
>= event
.m_x
) &&
724 (child
->m_y
+child
->m_height
>= event
.m_y
))
727 event
.m_x
-= child
->m_x
;
728 event
.m_y
-= child
->m_y
;
736 event
.SetEventObject( win
);
738 gs_timeLastClick
= gdk_event
->time
;
740 if (win
->GetEventHandler()->ProcessEvent( event
))
742 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "button_press_event" );
749 //-----------------------------------------------------------------------------
750 // "button_release_event"
751 //-----------------------------------------------------------------------------
753 static gint
gtk_window_button_release_callback( GtkWidget
*widget
, GdkEventButton
*gdk_event
, wxWindow
*win
)
755 if (g_isIdle
) wxapp_install_idle_handler();
757 if (!win
->HasVMT()) return FALSE
;
758 if (g_blockEventsOnDrag
) return FALSE
;
759 if (g_blockEventsOnScroll
) return FALSE
;
761 if (!win
->IsOwnGtkWindow( gdk_event
->window
)) return FALSE
;
764 printf( "OnButtonRelease from " );
765 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
766 printf( win->GetClassInfo()->GetClassName() );
770 wxEventType event_type
= wxEVT_NULL
;
772 switch (gdk_event
->button
)
774 case 1: event_type
= wxEVT_LEFT_UP
; break;
775 case 2: event_type
= wxEVT_MIDDLE_UP
; break;
776 case 3: event_type
= wxEVT_RIGHT_UP
; break;
779 wxMouseEvent
event( event_type
);
780 event
.m_shiftDown
= (gdk_event
->state
& GDK_SHIFT_MASK
);
781 event
.m_controlDown
= (gdk_event
->state
& GDK_CONTROL_MASK
);
782 event
.m_altDown
= (gdk_event
->state
& GDK_MOD1_MASK
);
783 event
.m_metaDown
= (gdk_event
->state
& GDK_MOD2_MASK
);
784 event
.m_leftDown
= (gdk_event
->state
& GDK_BUTTON1_MASK
);
785 event
.m_middleDown
= (gdk_event
->state
& GDK_BUTTON2_MASK
);
786 event
.m_rightDown
= (gdk_event
->state
& GDK_BUTTON3_MASK
);
787 event
.m_x
= (long)gdk_event
->x
;
788 event
.m_y
= (long)gdk_event
->y
;
790 // Some control don't have their own X window and thus cannot get
795 wxNode
*node
= win
->GetChildren().First();
798 wxWindow
*child
= (wxWindow
*)node
->Data();
800 if (child
->m_isStaticBox
)
802 // wxStaticBox is transparent in the box itself
805 int xx1
= child
->m_x
;
806 int yy1
= child
->m_y
;
807 int xx2
= child
->m_x
+ child
->m_width
;
808 int yy2
= child
->m_x
+ child
->m_height
;
811 if (((x
>= xx1
) && (x
<= xx1
+10) && (y
>= yy1
) && (y
<= yy2
)) ||
813 ((x
>= xx2
-10) && (x
<= xx2
) && (y
>= yy1
) && (y
<= yy2
)) ||
815 ((x
>= xx1
) && (x
<= xx2
) && (y
>= yy1
) && (y
<= yy1
+10)) ||
817 ((x
>= xx1
) && (x
<= xx2
) && (y
>= yy2
-1) && (y
<= yy2
)))
820 event
.m_x
-= child
->m_x
;
821 event
.m_y
-= child
->m_y
;
828 if ((child
->m_wxwindow
== (GtkWidget
*) NULL
) &&
829 (child
->m_x
<= event
.m_x
) &&
830 (child
->m_y
<= event
.m_y
) &&
831 (child
->m_x
+child
->m_width
>= event
.m_x
) &&
832 (child
->m_y
+child
->m_height
>= event
.m_y
))
835 event
.m_x
-= child
->m_x
;
836 event
.m_y
-= child
->m_y
;
844 event
.SetEventObject( win
);
846 if (win
->GetEventHandler()->ProcessEvent( event
))
848 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "button_release_event" );
855 //-----------------------------------------------------------------------------
856 // "motion_notify_event"
857 //-----------------------------------------------------------------------------
859 static gint
gtk_window_motion_notify_callback( GtkWidget
*widget
, GdkEventMotion
*gdk_event
, wxWindow
*win
)
861 if (g_isIdle
) wxapp_install_idle_handler();
863 if (!win
->HasVMT()) return FALSE
;
864 if (g_blockEventsOnDrag
) return FALSE
;
865 if (g_blockEventsOnScroll
) return FALSE
;
867 if (!win
->IsOwnGtkWindow( gdk_event
->window
)) return FALSE
;
869 if (gdk_event
->is_hint
)
873 GdkModifierType state
;
874 gdk_window_get_pointer(gdk_event
->window
, &x
, &y
, &state
);
877 gdk_event
->state
= state
;
881 printf( "OnMotion from " );
882 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
883 printf( win->GetClassInfo()->GetClassName() );
887 wxMouseEvent
event( wxEVT_MOTION
);
888 event
.m_shiftDown
= (gdk_event
->state
& GDK_SHIFT_MASK
);
889 event
.m_controlDown
= (gdk_event
->state
& GDK_CONTROL_MASK
);
890 event
.m_altDown
= (gdk_event
->state
& GDK_MOD1_MASK
);
891 event
.m_metaDown
= (gdk_event
->state
& GDK_MOD2_MASK
);
892 event
.m_leftDown
= (gdk_event
->state
& GDK_BUTTON1_MASK
);
893 event
.m_middleDown
= (gdk_event
->state
& GDK_BUTTON2_MASK
);
894 event
.m_rightDown
= (gdk_event
->state
& GDK_BUTTON3_MASK
);
896 event
.m_x
= (long)gdk_event
->x
;
897 event
.m_y
= (long)gdk_event
->y
;
899 // Some control don't have their own X window and thus cannot get
904 wxNode
*node
= win
->GetChildren().First();
907 wxWindow
*child
= (wxWindow
*)node
->Data();
909 if (child
->m_isStaticBox
)
911 // wxStaticBox is transparent in the box itself
914 int xx1
= child
->m_x
;
915 int yy1
= child
->m_y
;
916 int xx2
= child
->m_x
+ child
->m_width
;
917 int yy2
= child
->m_x
+ child
->m_height
;
920 if (((x
>= xx1
) && (x
<= xx1
+10) && (y
>= yy1
) && (y
<= yy2
)) ||
922 ((x
>= xx2
-10) && (x
<= xx2
) && (y
>= yy1
) && (y
<= yy2
)) ||
924 ((x
>= xx1
) && (x
<= xx2
) && (y
>= yy1
) && (y
<= yy1
+10)) ||
926 ((x
>= xx1
) && (x
<= xx2
) && (y
>= yy2
-1) && (y
<= yy2
)))
929 event
.m_x
-= child
->m_x
;
930 event
.m_y
-= child
->m_y
;
937 if ((child
->m_wxwindow
== (GtkWidget
*) NULL
) &&
938 (child
->m_x
<= event
.m_x
) &&
939 (child
->m_y
<= event
.m_y
) &&
940 (child
->m_x
+child
->m_width
>= event
.m_x
) &&
941 (child
->m_y
+child
->m_height
>= event
.m_y
))
944 event
.m_x
-= child
->m_x
;
945 event
.m_y
-= child
->m_y
;
953 event
.SetEventObject( win
);
955 if (win
->GetEventHandler()->ProcessEvent( event
))
957 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "motion_notify_event" );
964 //-----------------------------------------------------------------------------
966 //-----------------------------------------------------------------------------
968 static gint
gtk_window_focus_in_callback( GtkWidget
*widget
, GdkEvent
*WXUNUSED(event
), wxWindow
*win
)
970 if (g_isIdle
) wxapp_install_idle_handler();
972 if (!win
->HasVMT()) return FALSE
;
973 if (g_blockEventsOnDrag
) return FALSE
;
979 if (GTK_WIDGET_CAN_FOCUS(win
->m_wxwindow
))
981 GTK_WIDGET_SET_FLAGS (win
->m_wxwindow
, GTK_HAS_FOCUS
);
983 printf( "SetFocus flag from " );
984 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
985 printf( win->GetClassInfo()->GetClassName() );
993 wxPrintf( _T("OnSetFocus from ") );
994 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
995 wxPrintf( win->GetClassInfo()->GetClassName() );
997 wxPrintf( win->GetLabel() );
998 wxPrintf( _T(".\n") );
1001 wxFocusEvent
event( wxEVT_SET_FOCUS
, win
->GetId() );
1002 event
.SetEventObject( win
);
1004 if (win
->GetEventHandler()->ProcessEvent( event
))
1006 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "focus_in_event" );
1013 //-----------------------------------------------------------------------------
1014 // "focus_out_event"
1015 //-----------------------------------------------------------------------------
1017 static gint
gtk_window_focus_out_callback( GtkWidget
*widget
, GdkEvent
*WXUNUSED(event
), wxWindow
*win
)
1019 if (g_isIdle
) wxapp_install_idle_handler();
1021 if (!win
->HasVMT()) return FALSE
;
1022 if (g_blockEventsOnDrag
) return FALSE
;
1024 if (win
->m_wxwindow
)
1026 if (GTK_WIDGET_CAN_FOCUS(win
->m_wxwindow
))
1027 GTK_WIDGET_UNSET_FLAGS (win
->m_wxwindow
, GTK_HAS_FOCUS
);
1031 wxPrintf( _T("OnKillFocus from ") );
1032 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
1033 wxPrintf( win->GetClassInfo()->GetClassName() );
1034 wxPrintf( _T(" ") );
1035 wxPrintf( win->GetLabel() );
1036 wxPrintf( _T(".\n") );
1039 wxFocusEvent
event( wxEVT_KILL_FOCUS
, win
->GetId() );
1040 event
.SetEventObject( win
);
1042 if (win
->GetEventHandler()->ProcessEvent( event
))
1044 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "focus_out_event" );
1051 //-----------------------------------------------------------------------------
1052 // "enter_notify_event"
1053 //-----------------------------------------------------------------------------
1055 static gint
gtk_window_enter_callback( GtkWidget
*widget
, GdkEventCrossing
*gdk_event
, wxWindow
*win
)
1057 if (g_isIdle
) wxapp_install_idle_handler();
1059 if (!win
->HasVMT()) return FALSE
;
1060 if (g_blockEventsOnDrag
) return FALSE
;
1062 if (widget
->window
!= gdk_event
->window
) return FALSE
;
1064 if ((widget
->window
) && (win
->m_cursor
.Ok()))
1065 gdk_window_set_cursor( widget
->window
, win
->m_cursor
.GetCursor() );
1068 printf( "OnEnter from " );
1069 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
1070 printf( win->GetClassInfo()->GetClassName() );
1074 wxMouseEvent
event( wxEVT_ENTER_WINDOW
);
1075 event
.SetEventObject( win
);
1079 GdkModifierType state
= (GdkModifierType
)0;
1081 gdk_window_get_pointer( widget
->window
, &x
, &y
, &state
);
1083 event
.m_shiftDown
= (state
& GDK_SHIFT_MASK
);
1084 event
.m_controlDown
= (state
& GDK_CONTROL_MASK
);
1085 event
.m_altDown
= (state
& GDK_MOD1_MASK
);
1086 event
.m_metaDown
= (state
& GDK_MOD2_MASK
);
1087 event
.m_leftDown
= (state
& GDK_BUTTON1_MASK
);
1088 event
.m_middleDown
= (state
& GDK_BUTTON2_MASK
);
1089 event
.m_rightDown
= (state
& GDK_BUTTON3_MASK
);
1091 event
.m_x
= (long)x
;
1092 event
.m_y
= (long)y
;
1094 if (win
->GetEventHandler()->ProcessEvent( event
))
1096 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "enter_notify_event" );
1103 //-----------------------------------------------------------------------------
1104 // "leave_notify_event"
1105 //-----------------------------------------------------------------------------
1107 static gint
gtk_window_leave_callback( GtkWidget
*widget
, GdkEventCrossing
*gdk_event
, wxWindow
*win
)
1109 if (g_isIdle
) wxapp_install_idle_handler();
1111 if (!win
->HasVMT()) return FALSE
;
1112 if (g_blockEventsOnDrag
) return FALSE
;
1114 if (widget
->window
!= gdk_event
->window
) return FALSE
;
1117 gdk_window_set_cursor( widget
->window
, wxSTANDARD_CURSOR
->GetCursor() );
1120 printf( "OnLeave from " );
1121 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
1122 printf( win->GetClassInfo()->GetClassName() );
1126 wxMouseEvent
event( wxEVT_LEAVE_WINDOW
);
1127 event
.SetEventObject( win
);
1131 GdkModifierType state
= (GdkModifierType
)0;
1133 gdk_window_get_pointer( widget
->window
, &x
, &y
, &state
);
1135 event
.m_shiftDown
= (state
& GDK_SHIFT_MASK
);
1136 event
.m_controlDown
= (state
& GDK_CONTROL_MASK
);
1137 event
.m_altDown
= (state
& GDK_MOD1_MASK
);
1138 event
.m_metaDown
= (state
& GDK_MOD2_MASK
);
1139 event
.m_leftDown
= (state
& GDK_BUTTON1_MASK
);
1140 event
.m_middleDown
= (state
& GDK_BUTTON2_MASK
);
1141 event
.m_rightDown
= (state
& GDK_BUTTON3_MASK
);
1143 event
.m_x
= (long)x
;
1144 event
.m_y
= (long)y
;
1146 if (win
->GetEventHandler()->ProcessEvent( event
))
1148 gtk_signal_emit_stop_by_name( GTK_OBJECT(widget
), "leave_notify_event" );
1155 //-----------------------------------------------------------------------------
1156 // "value_changed" from m_vAdjust
1157 //-----------------------------------------------------------------------------
1159 static void gtk_window_vscroll_callback( GtkWidget
*WXUNUSED(widget
), wxWindow
*win
)
1161 if (g_isIdle
) wxapp_install_idle_handler();
1163 if (g_blockEventsOnDrag
) return;
1166 printf( "OnVScroll from " );
1167 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
1168 printf( win->GetClassInfo()->GetClassName() );
1172 if (!win
->HasVMT()) return;
1174 float diff
= win
->m_vAdjust
->value
- win
->m_oldVerticalPos
;
1175 if (fabs(diff
) < 0.2) return;
1176 win
->m_oldVerticalPos
= win
->m_vAdjust
->value
;
1178 wxEventType command
= wxEVT_NULL
;
1180 float line_step
= win
->m_vAdjust
->step_increment
;
1181 float page_step
= win
->m_vAdjust
->page_increment
;
1183 if (win
->m_isScrolling
)
1185 command
= wxEVT_SCROLL_THUMBTRACK
;
1189 if (fabs(win
->m_vAdjust
->value
-win
->m_vAdjust
->lower
) < 0.2) command
= wxEVT_SCROLL_BOTTOM
;
1190 else if (fabs(win
->m_vAdjust
->value
-win
->m_vAdjust
->upper
) < 0.2) command
= wxEVT_SCROLL_TOP
;
1191 else if (fabs(diff
-line_step
) < 0.2) command
= wxEVT_SCROLL_LINEDOWN
;
1192 else if (fabs(diff
+line_step
) < 0.2) command
= wxEVT_SCROLL_LINEUP
;
1193 else if (fabs(diff
-page_step
) < 0.2) command
= wxEVT_SCROLL_PAGEDOWN
;
1194 else if (fabs(diff
+page_step
) < 0.2) command
= wxEVT_SCROLL_PAGEUP
;
1195 else command
= wxEVT_SCROLL_THUMBTRACK
;
1198 int value
= (int)(win
->m_vAdjust
->value
+0.5);
1200 wxScrollEvent
event( command
, win
->GetId(), value
, wxVERTICAL
);
1201 event
.SetEventObject( win
);
1202 win
->GetEventHandler()->ProcessEvent( event
);
1205 //-----------------------------------------------------------------------------
1206 // "value_changed" from m_hAdjust
1207 //-----------------------------------------------------------------------------
1209 static void gtk_window_hscroll_callback( GtkWidget
*WXUNUSED(widget
), wxWindow
*win
)
1211 if (g_isIdle
) wxapp_install_idle_handler();
1213 if (g_blockEventsOnDrag
) return;
1216 printf( "OnHScroll from " );
1217 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
1218 printf( win->GetClassInfo()->GetClassName() );
1222 if (!win
->HasVMT()) return;
1224 float diff
= win
->m_hAdjust
->value
- win
->m_oldHorizontalPos
;
1225 if (fabs(diff
) < 0.2) return;
1226 win
->m_oldHorizontalPos
= win
->m_hAdjust
->value
;
1228 wxEventType command
= wxEVT_NULL
;
1230 float line_step
= win
->m_hAdjust
->step_increment
;
1231 float page_step
= win
->m_hAdjust
->page_increment
;
1233 if (win
->m_isScrolling
)
1235 command
= wxEVT_SCROLL_THUMBTRACK
;
1239 if (fabs(win
->m_hAdjust
->value
-win
->m_hAdjust
->lower
) < 0.2) command
= wxEVT_SCROLL_BOTTOM
;
1240 else if (fabs(win
->m_hAdjust
->value
-win
->m_hAdjust
->upper
) < 0.2) command
= wxEVT_SCROLL_TOP
;
1241 else if (fabs(diff
-line_step
) < 0.2) command
= wxEVT_SCROLL_LINEDOWN
;
1242 else if (fabs(diff
+line_step
) < 0.2) command
= wxEVT_SCROLL_LINEUP
;
1243 else if (fabs(diff
-page_step
) < 0.2) command
= wxEVT_SCROLL_PAGEDOWN
;
1244 else if (fabs(diff
+page_step
) < 0.2) command
= wxEVT_SCROLL_PAGEUP
;
1245 else command
= wxEVT_SCROLL_THUMBTRACK
;
1248 int value
= (int)(win
->m_hAdjust
->value
+0.5);
1250 wxScrollEvent
event( command
, win
->GetId(), value
, wxHORIZONTAL
);
1251 event
.SetEventObject( win
);
1252 win
->GetEventHandler()->ProcessEvent( event
);
1255 //-----------------------------------------------------------------------------
1256 // "changed" from m_vAdjust
1257 //-----------------------------------------------------------------------------
1259 static void gtk_window_vscroll_change_callback( GtkWidget
*WXUNUSED(widget
), wxWindow
*win
)
1261 if (g_isIdle
) wxapp_install_idle_handler();
1263 if (g_blockEventsOnDrag
) return;
1266 printf( "OnVScroll change from " );
1267 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
1268 printf( win->GetClassInfo()->GetClassName() );
1272 if (!win
->HasVMT()) return;
1274 wxEventType command
= wxEVT_SCROLL_THUMBTRACK
;
1275 int value
= (int)(win
->m_vAdjust
->value
+0.5);
1277 wxScrollEvent
event( command
, win
->GetId(), value
, wxVERTICAL
);
1278 event
.SetEventObject( win
);
1279 win
->GetEventHandler()->ProcessEvent( event
);
1282 //-----------------------------------------------------------------------------
1283 // "changed" from m_hAdjust
1284 //-----------------------------------------------------------------------------
1286 static void gtk_window_hscroll_change_callback( GtkWidget
*WXUNUSED(widget
), wxWindow
*win
)
1288 if (g_isIdle
) wxapp_install_idle_handler();
1290 if (g_blockEventsOnDrag
) return;
1293 printf( "OnHScroll change from " );
1294 if (win->GetClassInfo() && win->GetClassInfo()->GetClassName())
1295 printf( win->GetClassInfo()->GetClassName() );
1299 if (!win
->HasVMT()) return;
1301 wxEventType command
= wxEVT_SCROLL_THUMBTRACK
;
1302 int value
= (int)(win
->m_hAdjust
->value
+0.5);
1304 wxScrollEvent
event( command
, win
->GetId(), value
, wxHORIZONTAL
);
1305 event
.SetEventObject( win
);
1306 win
->GetEventHandler()->ProcessEvent( event
);
1309 //-----------------------------------------------------------------------------
1310 // "button_press_event" from scrollbar
1311 //-----------------------------------------------------------------------------
1313 static gint
gtk_scrollbar_button_press_callback( GtkRange
*WXUNUSED(widget
),
1314 GdkEventButton
*WXUNUSED(gdk_event
),
1317 if (g_isIdle
) wxapp_install_idle_handler();
1319 // don't test here as we can release the mouse while being over
1320 // a different window then the slider
1322 // if (gdk_event->window != widget->slider) return FALSE;
1324 win
->m_isScrolling
= TRUE
;
1325 g_blockEventsOnScroll
= TRUE
;
1330 //-----------------------------------------------------------------------------
1331 // "button_release_event" from scrollbar
1332 //-----------------------------------------------------------------------------
1334 static gint
gtk_scrollbar_button_release_callback( GtkRange
*widget
,
1335 GdkEventButton
*WXUNUSED(gdk_event
),
1338 if (g_isIdle
) wxapp_install_idle_handler();
1340 // don't test here as we can release the mouse while being over
1341 // a different window then the slider
1343 // if (gdk_event->window != widget->slider) return FALSE;
1345 GtkScrolledWindow
*s_window
= GTK_SCROLLED_WINDOW(win
->m_widget
);
1347 if (widget
== GTK_RANGE(s_window
->vscrollbar
))
1348 gtk_signal_emit_by_name( GTK_OBJECT(win
->m_hAdjust
), "value_changed" );
1350 gtk_signal_emit_by_name( GTK_OBJECT(win
->m_vAdjust
), "value_changed" );
1352 win
->m_isScrolling
= FALSE
;
1353 g_blockEventsOnScroll
= FALSE
;
1358 //-----------------------------------------------------------------------------
1359 // "realize" from m_widget
1360 //-----------------------------------------------------------------------------
1362 /* we cannot set colours, fonts and cursors before the widget has
1363 been realized, so we do this directly after realization */
1366 gtk_window_realized_callback( GtkWidget
*widget
, wxWindow
*win
)
1368 if (g_isIdle
) wxapp_install_idle_handler();
1370 if (win
->m_font
!= *wxSWISS_FONT
)
1372 wxFont
font( win
->m_font
);
1373 win
->m_font
= wxNullFont
;
1374 win
->SetFont( font
);
1377 if (win
->m_backgroundColour
!= wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE
))
1379 wxColour
bg( win
->m_backgroundColour
);
1380 win
->m_backgroundColour
= wxNullColour
;
1381 win
->SetBackgroundColour( bg
);
1384 if (win
->m_foregroundColour
!= *wxBLACK
)
1386 wxColour
fg( win
->m_foregroundColour
);
1387 win
->m_foregroundColour
= wxNullColour
;
1388 win
->SetForegroundColour( fg
);
1391 wxCursor
cursor( win
->m_cursor
);
1392 win
->m_cursor
= wxNullCursor
;
1393 win
->SetCursor( cursor
);
1398 //-----------------------------------------------------------------------------
1399 // InsertChild for wxWindow.
1400 //-----------------------------------------------------------------------------
1402 /* Callback for wxWindow. This very strange beast has to be used because
1403 * C++ has no virtual methods in a constructor. We have to emulate a
1404 * virtual function here as wxNotebook requires a different way to insert
1405 * a child in it. I had opted for creating a wxNotebookPage window class
1406 * which would have made this superfluous (such in the MDI window system),
1407 * but no-one was listening to me... */
1409 static void wxInsertChildInWindow( wxWindow
* parent
, wxWindow
* child
)
1411 gtk_myfixed_put( GTK_MYFIXED(parent
->m_wxwindow
),
1412 GTK_WIDGET(child
->m_widget
),
1416 gtk_widget_set_usize( GTK_WIDGET(child
->m_widget
),
1420 if (parent
->m_windowStyle
& wxTAB_TRAVERSAL
)
1422 /* we now allow a window to get the focus as long as it
1423 doesn't have any children. */
1424 GTK_WIDGET_UNSET_FLAGS( parent
->m_wxwindow
, GTK_CAN_FOCUS
);
1428 //-----------------------------------------------------------------------------
1430 //-----------------------------------------------------------------------------
1432 wxWindow
* wxGetActiveWindow()
1434 return g_focusWindow
;
1437 //-----------------------------------------------------------------------------
1439 //-----------------------------------------------------------------------------
1441 IMPLEMENT_DYNAMIC_CLASS(wxWindow
,wxEvtHandler
)
1443 BEGIN_EVENT_TABLE(wxWindow
, wxEvtHandler
)
1444 EVT_SIZE(wxWindow::OnSize
)
1445 EVT_SYS_COLOUR_CHANGED(wxWindow::OnSysColourChanged
)
1446 EVT_INIT_DIALOG(wxWindow::OnInitDialog
)
1447 EVT_KEY_DOWN(wxWindow::OnKeyDown
)
1450 void wxWindow::Init()
1454 m_widget
= (GtkWidget
*) NULL
;
1455 m_wxwindow
= (GtkWidget
*) NULL
;
1456 m_parent
= (wxWindow
*) NULL
;
1457 m_children
.DeleteContents( FALSE
);
1470 m_eventHandler
= this;
1471 m_windowValidator
= (wxValidator
*) NULL
;
1475 m_cursor
= *wxSTANDARD_CURSOR
;
1476 m_font
= *wxSWISS_FONT
;
1478 m_windowName
= "noname";
1480 m_constraints
= (wxLayoutConstraints
*) NULL
;
1481 m_constraintsInvolvedIn
= (wxList
*) NULL
;
1482 m_windowSizer
= (wxSizer
*) NULL
;
1483 m_sizerParent
= (wxWindow
*) NULL
;
1484 m_autoLayout
= FALSE
;
1488 m_needParent
= TRUE
;
1490 m_hasScrolling
= FALSE
;
1491 m_isScrolling
= FALSE
;
1492 m_hAdjust
= (GtkAdjustment
*) NULL
;
1493 m_vAdjust
= (GtkAdjustment
*) NULL
;
1494 m_oldHorizontalPos
= 0.0;
1495 m_oldVerticalPos
= 0.0;
1500 #if wxUSE_DRAG_AND_DROP
1501 m_dropTarget
= (wxDropTarget
*) NULL
;
1504 m_scrollGC
= (GdkGC
*) NULL
;
1505 m_widgetStyle
= (GtkStyle
*) NULL
;
1507 m_insertCallback
= wxInsertChildInWindow
;
1509 m_clientObject
= (wxClientData
*) NULL
;
1510 m_clientData
= NULL
;
1512 m_isStaticBox
= FALSE
;
1513 m_acceptsFocus
= FALSE
;
1516 m_toolTip
= (wxToolTip
*) NULL
;
1517 #endif // wxUSE_TOOLTIPS
1520 wxWindow::wxWindow()
1525 wxWindow::wxWindow( wxWindow
*parent
, wxWindowID id
,
1526 const wxPoint
&pos
, const wxSize
&size
,
1527 long style
, const wxString
&name
)
1531 Create( parent
, id
, pos
, size
, style
, name
);
1534 bool wxWindow::Create( wxWindow
*parent
, wxWindowID id
,
1535 const wxPoint
&pos
, const wxSize
&size
,
1536 long style
, const wxString
&name
)
1538 wxASSERT_MSG( m_isWindow
, _T("Init() must have been called before!") );
1540 PreCreation( parent
, id
, pos
, size
, style
, name
);
1542 m_widget
= gtk_scrolled_window_new( (GtkAdjustment
*) NULL
, (GtkAdjustment
*) NULL
);
1543 GTK_WIDGET_UNSET_FLAGS( m_widget
, GTK_CAN_FOCUS
);
1545 GtkScrolledWindow
*s_window
= GTK_SCROLLED_WINDOW(m_widget
);
1547 GtkScrolledWindowClass
*scroll_class
= GTK_SCROLLED_WINDOW_CLASS( GTK_OBJECT(m_widget
)->klass
);
1548 scroll_class
->scrollbar_spacing
= 0;
1550 gtk_scrolled_window_set_policy( s_window
, GTK_POLICY_AUTOMATIC
, GTK_POLICY_AUTOMATIC
);
1552 m_oldHorizontalPos
= 0.0;
1553 m_oldVerticalPos
= 0.0;
1555 m_hAdjust
= gtk_range_get_adjustment( GTK_RANGE(s_window
->hscrollbar
) );
1556 m_vAdjust
= gtk_range_get_adjustment( GTK_RANGE(s_window
->vscrollbar
) );
1558 m_wxwindow
= gtk_myfixed_new();
1559 gtk_widget_show( m_wxwindow
);
1561 gtk_container_add( GTK_CONTAINER(m_widget
), m_wxwindow
);
1563 #if (GTK_MINOR_VERSION > 0)
1564 GtkMyFixed
*myfixed
= GTK_MYFIXED(m_wxwindow
);
1566 if (m_windowStyle
& wxRAISED_BORDER
)
1568 gtk_myfixed_set_shadow_type( myfixed
, GTK_SHADOW_OUT
);
1570 else if (m_windowStyle
& wxSUNKEN_BORDER
)
1572 gtk_myfixed_set_shadow_type( myfixed
, GTK_SHADOW_IN
);
1576 gtk_myfixed_set_shadow_type( myfixed
, GTK_SHADOW_NONE
);
1579 GtkViewport
*viewport
= GTK_VIEWPORT(s_window
->viewport
);
1581 if (m_windowStyle
& wxRAISED_BORDER
)
1583 gtk_viewport_set_shadow_type( viewport
, GTK_SHADOW_OUT
);
1585 else if (m_windowStyle
& wxSUNKEN_BORDER
)
1587 gtk_viewport_set_shadow_type( viewport
, GTK_SHADOW_IN
);
1591 gtk_viewport_set_shadow_type( viewport
, GTK_SHADOW_NONE
);
1595 /* we always allow a window to get the focus as long as it
1596 doesn't have any children. */
1597 if (m_windowStyle
& wxTAB_TRAVERSAL
)
1599 GTK_WIDGET_SET_FLAGS( m_wxwindow
, GTK_CAN_FOCUS
);
1600 m_acceptsFocus
= FALSE
;
1604 GTK_WIDGET_SET_FLAGS( m_wxwindow
, GTK_CAN_FOCUS
);
1605 m_acceptsFocus
= TRUE
;
1608 /* grab the actual focus */
1609 gtk_widget_grab_focus( m_wxwindow
);
1611 #if (GTK_MINOR_VERSION == 0)
1612 // shut the viewport up
1613 gtk_viewport_set_hadjustment( viewport
, (GtkAdjustment
*) gtk_adjustment_new( 0.0, 0.0, 0.0, 0.0, 0.0, 0.0) );
1614 gtk_viewport_set_vadjustment( viewport
, (GtkAdjustment
*) gtk_adjustment_new( 0.0, 0.0, 0.0, 0.0, 0.0, 0.0) );
1617 // I _really_ don't want scrollbars in the beginning
1618 m_vAdjust
->lower
= 0.0;
1619 m_vAdjust
->upper
= 1.0;
1620 m_vAdjust
->value
= 0.0;
1621 m_vAdjust
->step_increment
= 1.0;
1622 m_vAdjust
->page_increment
= 1.0;
1623 m_vAdjust
->page_size
= 5.0;
1624 gtk_signal_emit_by_name( GTK_OBJECT(m_vAdjust
), "changed" );
1625 m_hAdjust
->lower
= 0.0;
1626 m_hAdjust
->upper
= 1.0;
1627 m_hAdjust
->value
= 0.0;
1628 m_hAdjust
->step_increment
= 1.0;
1629 m_hAdjust
->page_increment
= 1.0;
1630 m_hAdjust
->page_size
= 5.0;
1631 gtk_signal_emit_by_name( GTK_OBJECT(m_hAdjust
), "changed" );
1633 // these handlers block mouse events to any window during scrolling
1634 // such as motion events and prevent GTK and wxWindows from fighting
1635 // over where the slider should be
1637 gtk_signal_connect( GTK_OBJECT(s_window
->vscrollbar
), "button_press_event",
1638 (GtkSignalFunc
)gtk_scrollbar_button_press_callback
, (gpointer
) this );
1640 gtk_signal_connect( GTK_OBJECT(s_window
->hscrollbar
), "button_press_event",
1641 (GtkSignalFunc
)gtk_scrollbar_button_press_callback
, (gpointer
) this );
1643 gtk_signal_connect( GTK_OBJECT(s_window
->vscrollbar
), "button_release_event",
1644 (GtkSignalFunc
)gtk_scrollbar_button_release_callback
, (gpointer
) this );
1646 gtk_signal_connect( GTK_OBJECT(s_window
->hscrollbar
), "button_release_event",
1647 (GtkSignalFunc
)gtk_scrollbar_button_release_callback
, (gpointer
) this );
1649 // these handlers get notified when screen updates are required either when
1650 // scrolling or when the window size (and therefore scrollbar configuration)
1653 gtk_signal_connect( GTK_OBJECT(m_hAdjust
), "value_changed",
1654 (GtkSignalFunc
) gtk_window_hscroll_callback
, (gpointer
) this );
1655 gtk_signal_connect( GTK_OBJECT(m_vAdjust
), "value_changed",
1656 (GtkSignalFunc
) gtk_window_vscroll_callback
, (gpointer
) this );
1658 gtk_signal_connect( GTK_OBJECT(m_hAdjust
), "changed",
1659 (GtkSignalFunc
) gtk_window_hscroll_change_callback
, (gpointer
) this );
1660 gtk_signal_connect(GTK_OBJECT(m_vAdjust
), "changed",
1661 (GtkSignalFunc
) gtk_window_vscroll_change_callback
, (gpointer
) this );
1663 if (m_parent
) m_parent
->AddChild( this );
1665 (m_parent
->m_insertCallback
)( m_parent
, this );
1674 wxWindow::~wxWindow()
1678 #if wxUSE_DRAG_AND_DROP
1681 delete m_dropTarget
;
1682 m_dropTarget
= (wxDropTarget
*) NULL
;
1690 m_toolTip
= (wxToolTip
*) NULL
;
1692 #endif // wxUSE_TOOLTIPS
1694 if (m_widget
) Show( FALSE
);
1698 if (m_parent
) m_parent
->RemoveChild( this );
1700 if (m_widgetStyle
) gtk_style_unref( m_widgetStyle
);
1702 if (m_scrollGC
) gdk_gc_unref( m_scrollGC
);
1704 if (m_wxwindow
) gtk_widget_destroy( m_wxwindow
);
1706 if (m_widget
) gtk_widget_destroy( m_widget
);
1708 DeleteRelatedConstraints();
1711 /* This removes any dangling pointers to this window
1712 * in other windows' constraintsInvolvedIn lists. */
1713 UnsetConstraints(m_constraints
);
1714 delete m_constraints
;
1715 m_constraints
= (wxLayoutConstraints
*) NULL
;
1720 delete m_windowSizer
;
1721 m_windowSizer
= (wxSizer
*) NULL
;
1723 /* If this is a child of a sizer, remove self from parent */
1724 if (m_sizerParent
) m_sizerParent
->RemoveChild((wxWindow
*)this);
1726 /* Just in case the window has been Closed, but
1727 * we're then deleting immediately: don't leave
1728 * dangling pointers. */
1729 wxPendingDelete
.DeleteObject(this);
1731 /* Just in case we've loaded a top-level window via
1732 * wxWindow::LoadNativeDialog but we weren't a dialog
1734 wxTopLevelWindows
.DeleteObject(this);
1736 if (m_windowValidator
) delete m_windowValidator
;
1738 if (m_clientObject
) delete m_clientObject
;
1741 void wxWindow::PreCreation( wxWindow
*parent
, wxWindowID id
,
1742 const wxPoint
&pos
, const wxSize
&size
,
1743 long style
, const wxString
&name
)
1745 wxASSERT_MSG( (!m_needParent
) || (parent
), _T("Need complete parent.") );
1747 m_widget
= (GtkWidget
*) NULL
;
1748 m_wxwindow
= (GtkWidget
*) NULL
;
1751 m_children
.DeleteContents( FALSE
);
1754 if (m_width
== -1) m_width
= 20;
1756 if (m_height
== -1) m_height
= 20;
1761 if (!m_needParent
) /* some reasonable defaults */
1765 m_x
= (gdk_screen_width () - m_width
) / 2;
1766 if (m_x
< 10) m_x
= 10;
1770 m_y
= (gdk_screen_height () - m_height
) / 2;
1771 if (m_y
< 10) m_y
= 10;
1782 m_eventHandler
= this;
1784 m_windowId
= id
== -1 ? wxNewId() : id
;
1788 m_cursor
= *wxSTANDARD_CURSOR
;
1789 m_font
= *wxSWISS_FONT
;
1790 m_backgroundColour
= wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE
);
1791 m_foregroundColour
= *wxBLACK
;
1792 m_windowStyle
= style
;
1793 m_windowName
= name
;
1795 m_constraints
= (wxLayoutConstraints
*) NULL
;
1796 m_constraintsInvolvedIn
= (wxList
*) NULL
;
1797 m_windowSizer
= (wxSizer
*) NULL
;
1798 m_sizerParent
= (wxWindow
*) NULL
;
1799 m_autoLayout
= FALSE
;
1801 m_hasScrolling
= FALSE
;
1802 m_isScrolling
= FALSE
;
1803 m_hAdjust
= (GtkAdjustment
*) NULL
;
1804 m_vAdjust
= (GtkAdjustment
*) NULL
;
1805 m_oldHorizontalPos
= 0.0;
1806 m_oldVerticalPos
= 0.0;
1811 #if wxUSE_DRAG_AND_DROP
1812 m_dropTarget
= (wxDropTarget
*) NULL
;
1815 m_windowValidator
= (wxValidator
*) NULL
;
1816 m_scrollGC
= (GdkGC
*) NULL
;
1817 m_widgetStyle
= (GtkStyle
*) NULL
;
1819 m_clientObject
= (wxClientData
*)NULL
;
1820 m_clientData
= NULL
;
1822 m_isStaticBox
= FALSE
;
1825 m_toolTip
= (wxToolTip
*) NULL
;
1826 #endif // wxUSE_TOOLTIPS
1829 void wxWindow::PostCreation()
1831 wxASSERT_MSG( (m_widget
!= NULL
), _T("invalid window") );
1835 /* these get reported to wxWindows -> wxPaintEvent */
1836 gtk_signal_connect( GTK_OBJECT(m_wxwindow
), "expose_event",
1837 GTK_SIGNAL_FUNC(gtk_window_expose_callback
), (gpointer
)this );
1839 gtk_signal_connect( GTK_OBJECT(m_wxwindow
), "draw",
1840 GTK_SIGNAL_FUNC(gtk_window_draw_callback
), (gpointer
)this );
1842 #if (GTK_MINOR_VERSION > 0)
1843 /* these are called when the "sunken" or "raised" borders are drawn */
1844 gtk_signal_connect( GTK_OBJECT(m_widget
), "expose_event",
1845 GTK_SIGNAL_FUNC(gtk_window_own_expose_callback
), (gpointer
)this );
1847 gtk_signal_connect( GTK_OBJECT(m_widget
), "draw",
1848 GTK_SIGNAL_FUNC(gtk_window_own_draw_callback
), (gpointer
)this );
1852 GtkWidget
*connect_widget
= GetConnectWidget();
1854 ConnectWidget( connect_widget
);
1856 /* we cannot set colours, fonts and cursors before the widget has
1857 been realized, so we do this directly after realization */
1858 gtk_signal_connect( GTK_OBJECT(connect_widget
), "realize",
1859 GTK_SIGNAL_FUNC(gtk_window_realized_callback
), (gpointer
) this );
1864 void wxWindow::ConnectWidget( GtkWidget
*widget
)
1866 gtk_signal_connect( GTK_OBJECT(widget
), "key_press_event",
1867 GTK_SIGNAL_FUNC(gtk_window_key_press_callback
), (gpointer
)this );
1869 gtk_signal_connect( GTK_OBJECT(widget
), "key_release_event",
1870 GTK_SIGNAL_FUNC(gtk_window_key_release_callback
), (gpointer
)this );
1872 gtk_signal_connect( GTK_OBJECT(widget
), "button_press_event",
1873 GTK_SIGNAL_FUNC(gtk_window_button_press_callback
), (gpointer
)this );
1875 gtk_signal_connect( GTK_OBJECT(widget
), "button_release_event",
1876 GTK_SIGNAL_FUNC(gtk_window_button_release_callback
), (gpointer
)this );
1878 gtk_signal_connect( GTK_OBJECT(widget
), "motion_notify_event",
1879 GTK_SIGNAL_FUNC(gtk_window_motion_notify_callback
), (gpointer
)this );
1881 gtk_signal_connect( GTK_OBJECT(widget
), "focus_in_event",
1882 GTK_SIGNAL_FUNC(gtk_window_focus_in_callback
), (gpointer
)this );
1884 gtk_signal_connect( GTK_OBJECT(widget
), "focus_out_event",
1885 GTK_SIGNAL_FUNC(gtk_window_focus_out_callback
), (gpointer
)this );
1887 gtk_signal_connect( GTK_OBJECT(widget
), "enter_notify_event",
1888 GTK_SIGNAL_FUNC(gtk_window_enter_callback
), (gpointer
)this );
1890 gtk_signal_connect( GTK_OBJECT(widget
), "leave_notify_event",
1891 GTK_SIGNAL_FUNC(gtk_window_leave_callback
), (gpointer
)this );
1894 bool wxWindow::HasVMT()
1899 bool wxWindow::Close( bool force
)
1901 wxASSERT_MSG( (m_widget
!= NULL
), _T("invalid window") );
1903 wxCloseEvent
event(wxEVT_CLOSE_WINDOW
, m_windowId
);
1904 event
.SetEventObject(this);
1905 event
.SetCanVeto(!force
);
1907 /* return FALSE if window wasn't closed because the application vetoed the
1909 return GetEventHandler()->ProcessEvent(event
) && !event
.GetVeto();
1912 bool wxWindow::Destroy()
1914 wxASSERT_MSG( (m_widget
!= NULL
), _T("invalid window") );
1921 bool wxWindow::DestroyChildren()
1924 while ((node
= m_children
.First()) != (wxNode
*)NULL
)
1927 if ((child
= (wxWindow
*)node
->Data()) != (wxWindow
*)NULL
)
1930 if (m_children
.Member(child
)) delete node
;
1936 void wxWindow::PrepareDC( wxDC
&WXUNUSED(dc
) )
1938 // are we to set fonts here ?
1941 void wxWindow::DoSetSize( int x
, int y
, int width
, int height
, int sizeFlags
)
1943 wxASSERT_MSG( (m_widget
!= NULL
), _T("invalid window") );
1944 wxASSERT_MSG( (m_parent
!= NULL
), _T("wxWindow::SetSize requires parent.\n") );
1946 if (m_resizing
) return; /* I don't like recursions */
1949 if (m_parent
->m_wxwindow
== NULL
) /* i.e. wxNotebook */
1951 /* don't set the size for children of wxNotebook, just take the values. */
1959 int old_width
= m_width
;
1960 int old_height
= m_height
;
1962 if ((sizeFlags
& wxSIZE_USE_EXISTING
) == wxSIZE_USE_EXISTING
)
1964 if (x
!= -1) m_x
= x
;
1965 if (y
!= -1) m_y
= y
;
1966 if (width
!= -1) m_width
= width
;
1967 if (height
!= -1) m_height
= height
;
1977 if ((sizeFlags
& wxSIZE_AUTO_WIDTH
) == wxSIZE_AUTO_WIDTH
)
1979 if (width
== -1) m_width
= 80;
1982 if ((sizeFlags
& wxSIZE_AUTO_HEIGHT
) == wxSIZE_AUTO_HEIGHT
)
1984 if (height
== -1) m_height
= 26;
1987 if ((m_minWidth
!= -1) && (m_width
< m_minWidth
)) m_width
= m_minWidth
;
1988 if ((m_minHeight
!= -1) && (m_height
< m_minHeight
)) m_height
= m_minHeight
;
1989 if ((m_maxWidth
!= -1) && (m_width
> m_maxWidth
)) m_width
= m_maxWidth
;
1990 if ((m_maxHeight
!= -1) && (m_height
> m_maxHeight
)) m_height
= m_maxHeight
;
1992 if (GTK_WIDGET_HAS_DEFAULT(m_widget
))
1994 /* the default button has a border around it */
1997 gtk_myfixed_move( GTK_MYFIXED(m_parent
->m_wxwindow
), m_widget
, m_x
-border
, m_y
-border
);
1999 gtk_widget_set_usize( m_widget
, m_width
+2*border
, m_height
+2*border
);
2003 gtk_myfixed_move( GTK_MYFIXED(m_parent
->m_wxwindow
), m_widget
, m_x
, m_y
);
2005 if ((old_width
!= m_width
) || (old_height
!= m_height
))
2006 gtk_widget_set_usize( m_widget
, m_width
, m_height
);
2012 wxSizeEvent
event( wxSize(m_width
,m_height
), GetId() );
2013 event
.SetEventObject( this );
2014 GetEventHandler()->ProcessEvent( event
);
2019 void wxWindow::OnInternalIdle()
2024 void wxWindow::GetSize( int *width
, int *height
) const
2026 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2028 if (width
) (*width
) = m_width
;
2029 if (height
) (*height
) = m_height
;
2032 void wxWindow::DoSetClientSize( int width
, int height
)
2034 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2038 SetSize( width
, height
);
2045 if (!m_hasScrolling
)
2047 GtkStyleClass
*window_class
= m_wxwindow
->style
->klass
;
2049 if ((m_windowStyle
& wxRAISED_BORDER
) ||
2050 (m_windowStyle
& wxSUNKEN_BORDER
))
2052 dw
+= 2 * window_class
->xthickness
;
2053 dh
+= 2 * window_class
->ythickness
;
2058 GtkScrolledWindow
*scroll_window
= GTK_SCROLLED_WINDOW(m_widget
);
2059 GtkScrolledWindowClass
*scroll_class
= GTK_SCROLLED_WINDOW_CLASS( GTK_OBJECT(m_widget
)->klass
);
2061 #if (GTK_MINOR_VERSION == 0)
2062 GtkWidget
*viewport
= scroll_window
->viewport
;
2063 GtkStyleClass
*viewport_class
= viewport
->style
->klass
;
2065 if ((m_windowStyle
& wxRAISED_BORDER
) ||
2066 (m_windowStyle
& wxSUNKEN_BORDER
))
2068 dw
+= 2 * viewport_class
->xthickness
;
2069 dh
+= 2 * viewport_class
->ythickness
;
2074 GtkWidget *hscrollbar = scroll_window->hscrollbar;
2075 GtkWidget *vscrollbar = scroll_window->vscrollbar;
2077 we use this instead: range.slider_width = 11 + 2*2pts edge
2080 if (scroll_window
->vscrollbar_visible
)
2082 dw
+= 15; /* dw += vscrollbar->allocation.width; */
2083 dw
+= scroll_class
->scrollbar_spacing
;
2086 if (scroll_window
->hscrollbar_visible
)
2088 dh
+= 15; /* dh += hscrollbar->allocation.height; */
2089 dw
+= scroll_class
->scrollbar_spacing
;
2093 SetSize( width
+dw
, height
+dh
);
2097 void wxWindow::GetClientSize( int *width
, int *height
) const
2099 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2103 if (width
) (*width
) = m_width
;
2104 if (height
) (*height
) = m_height
;
2111 if (!m_hasScrolling
)
2113 GtkStyleClass
*window_class
= m_wxwindow
->style
->klass
;
2115 if ((m_windowStyle
& wxRAISED_BORDER
) ||
2116 (m_windowStyle
& wxSUNKEN_BORDER
))
2118 dw
+= 2 * window_class
->xthickness
;
2119 dh
+= 2 * window_class
->ythickness
;
2124 GtkScrolledWindow
*scroll_window
= GTK_SCROLLED_WINDOW(m_widget
);
2125 GtkScrolledWindowClass
*scroll_class
= GTK_SCROLLED_WINDOW_CLASS( GTK_OBJECT(m_widget
)->klass
);
2127 #if (GTK_MINOR_VERSION == 0)
2128 GtkWidget
*viewport
= scroll_window
->viewport
;
2129 GtkStyleClass
*viewport_class
= viewport
->style
->klass
;
2131 if ((m_windowStyle
& wxRAISED_BORDER
) ||
2132 (m_windowStyle
& wxSUNKEN_BORDER
))
2134 dw
+= 2 * viewport_class
->xthickness
;
2135 dh
+= 2 * viewport_class
->ythickness
;
2139 GtkWidget *hscrollbar = scroll_window->hscrollbar;
2140 GtkWidget *vscrollbar = scroll_window->vscrollbar;
2142 we use this instead: range.slider_width = 11 + 2*2pts edge
2145 if (scroll_window
->vscrollbar_visible
)
2147 dw
+= 15; /* dw += vscrollbar->allocation.width; */
2148 dw
+= scroll_class
->scrollbar_spacing
;
2151 if (scroll_window
->hscrollbar_visible
)
2153 dh
+= 15; /* dh += hscrollbar->allocation.height; */
2154 dh
+= scroll_class
->scrollbar_spacing
;
2158 if (width
) (*width
) = m_width
- dw
;
2159 if (height
) (*height
) = m_height
- dh
;
2163 void wxWindow::GetPosition( int *x
, int *y
) const
2165 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2171 void wxWindow::ClientToScreen( int *x
, int *y
)
2173 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2175 if (!m_widget
->window
) return;
2177 GdkWindow
*source
= (GdkWindow
*) NULL
;
2179 source
= m_wxwindow
->window
;
2181 source
= m_widget
->window
;
2185 gdk_window_get_origin( source
, &org_x
, &org_y
);
2189 if (GTK_WIDGET_NO_WINDOW (m_widget
))
2191 org_x
+= m_widget
->allocation
.x
;
2192 org_y
+= m_widget
->allocation
.y
;
2200 void wxWindow::ScreenToClient( int *x
, int *y
)
2202 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2204 if (!m_widget
->window
) return;
2206 GdkWindow
*source
= (GdkWindow
*) NULL
;
2208 source
= m_wxwindow
->window
;
2210 source
= m_widget
->window
;
2214 gdk_window_get_origin( source
, &org_x
, &org_y
);
2218 if (GTK_WIDGET_NO_WINDOW (m_widget
))
2220 org_x
+= m_widget
->allocation
.x
;
2221 org_y
+= m_widget
->allocation
.y
;
2229 void wxWindow::Centre( int direction
)
2231 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2240 m_parent
->GetSize( &p_w
, &p_h
);
2241 if (direction
& wxHORIZONTAL
== wxHORIZONTAL
) x
= (p_w
- m_width
) / 2;
2242 if (direction
& wxVERTICAL
== wxVERTICAL
) y
= (p_h
- m_height
) / 2;
2246 if (direction
& wxHORIZONTAL
== wxHORIZONTAL
) x
= (gdk_screen_width () - m_width
) / 2;
2247 if (direction
& wxVERTICAL
== wxVERTICAL
) y
= (gdk_screen_height () - m_height
) / 2;
2253 void wxWindow::Fit()
2255 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2259 wxNode
*node
= m_children
.First();
2262 wxWindow
*win
= (wxWindow
*)node
->Data();
2264 win
->GetPosition(&wx
, &wy
);
2265 win
->GetSize(&ww
, &wh
);
2266 if (wx
+ ww
> maxX
) maxX
= wx
+ ww
;
2267 if (wy
+ wh
> maxY
) maxY
= wy
+ wh
;
2269 node
= node
->Next();
2272 SetClientSize(maxX
+ 7, maxY
+ 14);
2275 void wxWindow::SetSizeHints( int minW
, int minH
, int maxW
, int maxH
, int WXUNUSED(incW
), int WXUNUSED(incH
) )
2277 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2285 void wxWindow::OnSize( wxSizeEvent
&WXUNUSED(event
) )
2287 // if (GetAutoLayout()) Layout();
2290 bool wxWindow::Show( bool show
)
2292 wxCHECK_MSG( (m_widget
!= NULL
), FALSE
, _T("invalid window") );
2294 if (show
== m_isShown
) return TRUE
;
2297 gtk_widget_show( m_widget
);
2299 gtk_widget_hide( m_widget
);
2306 void wxWindow::Enable( bool enable
)
2308 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2310 m_isEnabled
= enable
;
2312 gtk_widget_set_sensitive( m_widget
, enable
);
2313 if (m_wxwindow
) gtk_widget_set_sensitive( m_wxwindow
, enable
);
2316 int wxWindow::GetCharHeight() const
2318 wxCHECK_MSG( (m_widget
!= NULL
), 12, _T("invalid window") );
2320 wxCHECK_MSG( m_font
.Ok(), 12, _T("invalid font") );
2322 GdkFont
*font
= m_font
.GetInternalFont( 1.0 );
2324 return font
->ascent
+ font
->descent
;
2327 int wxWindow::GetCharWidth() const
2329 wxCHECK_MSG( (m_widget
!= NULL
), 8, _T("invalid window") );
2331 wxCHECK_MSG( m_font
.Ok(), 8, _T("invalid font") );
2333 GdkFont
*font
= m_font
.GetInternalFont( 1.0 );
2335 return gdk_string_width( font
, "H" );
2338 void wxWindow::GetTextExtent( const wxString
& string
, int *x
, int *y
,
2339 int *descent
, int *externalLeading
, const wxFont
*theFont
, bool WXUNUSED(use16
) ) const
2341 wxFont fontToUse
= m_font
;
2342 if (theFont
) fontToUse
= *theFont
;
2344 wxCHECK_RET( fontToUse
.Ok(), _T("invalid font") );
2346 GdkFont
*font
= fontToUse
.GetInternalFont( 1.0 );
2347 if (x
) (*x
) = gdk_string_width( font
, string
.mbc_str() );
2348 if (y
) (*y
) = font
->ascent
+ font
->descent
;
2349 if (descent
) (*descent
) = font
->descent
;
2350 if (externalLeading
) (*externalLeading
) = 0; // ??
2353 void wxWindow::MakeModal( bool modal
)
2357 // Disable all other windows
2358 if (this->IsKindOf(CLASSINFO(wxDialog
)) || this->IsKindOf(CLASSINFO(wxFrame
)))
2360 wxNode
*node
= wxTopLevelWindows
.First();
2363 wxWindow
*win
= (wxWindow
*)node
->Data();
2364 if (win
!= this) win
->Enable(!modal
);
2366 node
= node
->Next();
2371 void wxWindow::OnKeyDown( wxKeyEvent
&event
)
2373 event
.SetEventType( wxEVT_CHAR
);
2375 if (!GetEventHandler()->ProcessEvent( event
))
2381 void wxWindow::SetFocus()
2383 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2385 GtkWidget
*connect_widget
= GetConnectWidget();
2388 if (GTK_WIDGET_CAN_FOCUS(connect_widget
) /*&& !GTK_WIDGET_HAS_FOCUS (connect_widget)*/ )
2390 gtk_widget_grab_focus (connect_widget
);
2392 else if (GTK_IS_CONTAINER(connect_widget
))
2394 gtk_container_focus( GTK_CONTAINER(connect_widget
), GTK_DIR_TAB_FORWARD
);
2402 wxWindow
*wxWindow::FindFocus()
2404 return g_focusWindow
;
2407 bool wxWindow::AcceptsFocus() const
2409 return IsEnabled() && IsShown() && m_acceptsFocus
;
2412 void wxWindow::AddChild( wxWindow
*child
)
2414 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2415 wxCHECK_RET( (child
!= NULL
), _T("invalid child") );
2417 m_children
.Append( child
);
2420 wxWindow
*wxWindow::ReParent( wxWindow
*newParent
)
2422 wxCHECK_MSG( (m_widget
!= NULL
), (wxWindow
*) NULL
, _T("invalid window") );
2424 wxWindow
*oldParent
= GetParent();
2426 if (oldParent
) oldParent
->RemoveChild( this );
2428 gtk_widget_unparent( m_widget
);
2432 newParent
->AddChild( this );
2433 (newParent
->m_insertCallback
)( newParent
, this );
2439 void wxWindow::RemoveChild( wxWindow
*child
)
2441 m_children
.DeleteObject( child
);
2442 child
->m_parent
= (wxWindow
*) NULL
;
2445 void wxWindow::SetReturnCode( int retCode
)
2447 m_retCode
= retCode
;
2450 int wxWindow::GetReturnCode()
2455 void wxWindow::Raise()
2457 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2459 if (!m_widget
->window
) return;
2461 if (m_widget
) gdk_window_raise( m_widget
->window
);
2464 void wxWindow::Lower()
2466 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2468 if (!m_widget
->window
) return;
2470 if (m_widget
) gdk_window_lower( m_widget
->window
);
2473 wxEvtHandler
*wxWindow::GetEventHandler() const
2475 return m_eventHandler
;
2478 void wxWindow::SetEventHandler( wxEvtHandler
*handler
)
2480 m_eventHandler
= handler
;
2483 void wxWindow::PushEventHandler(wxEvtHandler
*handler
)
2485 handler
->SetNextHandler(GetEventHandler());
2486 SetEventHandler(handler
);
2489 wxEvtHandler
*wxWindow::PopEventHandler(bool deleteHandler
)
2491 if (GetEventHandler())
2493 wxEvtHandler
*handlerA
= GetEventHandler();
2494 wxEvtHandler
*handlerB
= handlerA
->GetNextHandler();
2495 handlerA
->SetNextHandler((wxEvtHandler
*) NULL
);
2496 SetEventHandler(handlerB
);
2500 return (wxEvtHandler
*) NULL
;
2506 return (wxEvtHandler
*) NULL
;
2509 wxValidator
*wxWindow::GetValidator()
2511 return m_windowValidator
;
2514 void wxWindow::SetValidator( const wxValidator
& validator
)
2516 if (m_windowValidator
) delete m_windowValidator
;
2517 m_windowValidator
= validator
.Clone();
2518 if (m_windowValidator
) m_windowValidator
->SetWindow(this);
2521 void wxWindow::SetClientObject( wxClientData
*data
)
2523 if (m_clientObject
) delete m_clientObject
;
2524 m_clientObject
= data
;
2527 wxClientData
*wxWindow::GetClientObject()
2529 return m_clientObject
;
2532 void wxWindow::SetClientData( void *data
)
2534 m_clientData
= data
;
2537 void *wxWindow::GetClientData()
2539 return m_clientData
;
2542 bool wxWindow::IsBeingDeleted()
2547 void wxWindow::SetId( wxWindowID id
)
2552 wxWindowID
wxWindow::GetId() const
2557 void wxWindow::SetCursor( const wxCursor
&cursor
)
2559 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2563 if (cursor
== m_cursor
) return;
2568 m_cursor
= *wxSTANDARD_CURSOR
;
2571 if (!m_widget
->window
) return;
2573 gdk_window_set_cursor( m_widget
->window
, m_cursor
.GetCursor() );
2575 if ((m_wxwindow
) && (m_wxwindow
->window
))
2576 gdk_window_set_cursor( m_wxwindow
->window
, m_cursor
.GetCursor() );
2579 void wxWindow::WarpPointer( int WXUNUSED(x
), int WXUNUSED(y
) )
2584 void wxWindow::Refresh( bool eraseBackground
, const wxRect
*rect
)
2586 wxCHECK_RET( (m_widget
!= NULL
), _T("invalid window") );
2588 if (!m_widget
->window
) return;
2590 if (eraseBackground
&& m_wxwindow
&& m_wxwindow
->window
)
2594 gdk_window_clear_area( m_wxwindow
->window
,
2596 rect
->width
, rect
->height
);
2600 gdk_window_clear( m_wxwindow
->window
);
2607 gtk_widget_draw( m_wxwindow
, (GdkRectangle
*) NULL
);
2609 gtk_widget_draw( m_widget
, (GdkRectangle
*) NULL
);
2613 GdkRectangle gdk_rect
;
2614 gdk_rect
.x
= rect
->x
;
2615 gdk_rect
.y
= rect
->y
;
2616 gdk_rect
.width
= rect
->width
;
2617 gdk_rect
.height
= rect
->height
;
2620 gtk_widget_draw( m_wxwindow
, &gdk_rect
);
2622 gtk_widget_draw( m_widget
, &gdk_rect
);
2626 wxRegion
wxWindow::GetUpdateRegion() const
2628 return m_updateRegion
;
2631 bool wxWindow::IsExposed( int x
, int y
) const
2633 return (m_updateRegion
.Contains( x
, y
) != wxOutRegion
);
2636 bool wxWindow::IsExposed( int x
, int y
, int w
, int h
) const
2638 return (m_updateRegion
.Contains( x
, y
, w
, h
) != wxOutRegion
);
2641 bool wxWindow::IsExposed( const wxPoint
& pt
) const
2643 return (m_updateRegion
.Contains( pt
.x
, pt
.y
) != wxOutRegion
);
2646 bool wxWindow::IsExposed( const wxRect
& rect
) const
2648 return (m_updateRegion
.Contains( rect
.x
, rect
.y
, rect
.width
, rect
.height
) != wxOutRegion
);
2651 void wxWindow::Clear()
2653 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
2655 if (!m_widget
->window
) return;
2657 if (m_wxwindow
&& m_wxwindow
->window
)
2659 gdk_window_clear( m_wxwindow
->window
);
2664 void wxWindow::SetToolTip( const wxString
&tip
)
2668 m_toolTip
->SetTip( tip
);
2672 SetToolTip( new wxToolTip( tip
) );
2675 // setting empty tooltip text does not remove the tooltip any more for
2676 // wxMSW compatibility - use SetToolTip((wxToolTip *)NULL) for this
2679 void wxWindow::SetToolTip( wxToolTip
*tip
)
2683 m_toolTip
->SetTip( (char*) NULL
);
2690 m_toolTip
->Apply( this );
2693 void wxWindow::ApplyToolTip( GtkTooltips
*tips
, const wxChar
*tip
)
2695 gtk_tooltips_set_tip( tips
, GetConnectWidget(), wxConv_current
->cWX2MB(tip
), (gchar
*) NULL
);
2697 #endif // wxUSE_TOOLTIPS
2699 wxColour
wxWindow::GetBackgroundColour() const
2701 return m_backgroundColour
;
2704 void wxWindow::SetBackgroundColour( const wxColour
&colour
)
2706 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
2708 if (m_backgroundColour
== colour
) return;
2710 m_backgroundColour
= colour
;
2711 if (!m_backgroundColour
.Ok()) return;
2713 GtkWidget
*connect_widget
= GetConnectWidget();
2714 if (!connect_widget
->window
) return;
2716 if (m_wxwindow
&& m_wxwindow
->window
)
2718 /* wxMSW doesn't clear the window here. I don't do that
2719 either to provide compatibility. call Clear() to do
2722 m_backgroundColour
.CalcPixel( gdk_window_get_colormap( m_wxwindow
->window
) );
2723 gdk_window_set_background( m_wxwindow
->window
, m_backgroundColour
.GetColor() );
2726 wxColour sysbg
= wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE
);
2728 if (sysbg
.Red() == colour
.Red() &&
2729 sysbg
.Green() == colour
.Green() &&
2730 sysbg
.Blue() == colour
.Blue())
2732 m_backgroundColour
= wxNullColour
;
2734 m_backgroundColour
= sysbg
;
2742 wxColour
wxWindow::GetForegroundColour() const
2744 return m_foregroundColour
;
2747 void wxWindow::SetForegroundColour( const wxColour
&colour
)
2749 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
2751 if (m_foregroundColour
== colour
) return;
2753 m_foregroundColour
= colour
;
2754 if (!m_foregroundColour
.Ok()) return;
2756 if (!m_widget
->window
) return;
2758 wxColour sysbg
= wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE
);
2759 if (sysbg
.Red() == colour
.Red() &&
2760 sysbg
.Green() == colour
.Green() &&
2761 sysbg
.Blue() == colour
.Blue())
2763 m_backgroundColour
= wxNullColour
;
2765 m_backgroundColour
= sysbg
;
2773 GtkStyle
*wxWindow::GetWidgetStyle()
2775 if (m_widgetStyle
) gtk_style_unref( m_widgetStyle
);
2779 gtk_widget_get_style( m_widget
) );
2781 return m_widgetStyle
;
2784 void wxWindow::SetWidgetStyle()
2786 GtkStyle
*style
= GetWidgetStyle();
2788 gdk_font_unref( style
->font
);
2789 style
->font
= gdk_font_ref( m_font
.GetInternalFont( 1.0 ) );
2791 if (m_foregroundColour
.Ok())
2793 m_foregroundColour
.CalcPixel( gdk_window_get_colormap( m_widget
->window
) );
2794 style
->fg
[GTK_STATE_NORMAL
] = *m_foregroundColour
.GetColor();
2795 style
->fg
[GTK_STATE_PRELIGHT
] = *m_foregroundColour
.GetColor();
2796 style
->fg
[GTK_STATE_ACTIVE
] = *m_foregroundColour
.GetColor();
2799 if (m_backgroundColour
.Ok())
2801 m_backgroundColour
.CalcPixel( gdk_window_get_colormap( m_widget
->window
) );
2802 style
->bg
[GTK_STATE_NORMAL
] = *m_backgroundColour
.GetColor();
2803 style
->base
[GTK_STATE_NORMAL
] = *m_backgroundColour
.GetColor();
2804 style
->bg
[GTK_STATE_PRELIGHT
] = *m_backgroundColour
.GetColor();
2805 style
->base
[GTK_STATE_PRELIGHT
] = *m_backgroundColour
.GetColor();
2806 style
->bg
[GTK_STATE_ACTIVE
] = *m_backgroundColour
.GetColor();
2807 style
->base
[GTK_STATE_ACTIVE
] = *m_backgroundColour
.GetColor();
2808 style
->bg
[GTK_STATE_INSENSITIVE
] = *m_backgroundColour
.GetColor();
2809 style
->base
[GTK_STATE_INSENSITIVE
] = *m_backgroundColour
.GetColor();
2813 void wxWindow::ApplyWidgetStyle()
2817 bool wxWindow::Validate()
2819 wxCHECK_MSG( m_widget
!= NULL
, FALSE
, _T("invalid window") );
2821 wxNode
*node
= m_children
.First();
2824 wxWindow
*child
= (wxWindow
*)node
->Data();
2825 if (child
->GetValidator() && /* child->GetValidator()->Ok() && */ !child
->GetValidator()->Validate(this))
2829 node
= node
->Next();
2834 bool wxWindow::TransferDataToWindow()
2836 wxCHECK_MSG( m_widget
!= NULL
, FALSE
, _T("invalid window") );
2838 wxNode
*node
= m_children
.First();
2841 wxWindow
*child
= (wxWindow
*)node
->Data();
2842 if (child
->GetValidator() && /* child->GetValidator()->Ok() && */
2843 !child
->GetValidator()->TransferToWindow() )
2845 wxMessageBox( _("Application Error"), _("Could not transfer data to window"), wxOK
|wxICON_EXCLAMATION
);
2848 node
= node
->Next();
2853 bool wxWindow::TransferDataFromWindow()
2855 wxCHECK_MSG( m_widget
!= NULL
, FALSE
, _T("invalid window") );
2857 wxNode
*node
= m_children
.First();
2860 wxWindow
*child
= (wxWindow
*)node
->Data();
2861 if ( child
->GetValidator() && /* child->GetValidator()->Ok() && */ !child
->GetValidator()->TransferFromWindow() )
2865 node
= node
->Next();
2870 void wxWindow::SetAcceleratorTable( const wxAcceleratorTable
& accel
)
2872 m_acceleratorTable
= accel
;
2875 void wxWindow::OnInitDialog( wxInitDialogEvent
&WXUNUSED(event
) )
2877 TransferDataToWindow();
2880 void wxWindow::InitDialog()
2882 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
2884 wxInitDialogEvent
event(GetId());
2885 event
.SetEventObject( this );
2886 GetEventHandler()->ProcessEvent(event
);
2889 static void SetInvokingWindow( wxMenu
*menu
, wxWindow
*win
)
2891 menu
->SetInvokingWindow( win
);
2892 wxNode
*node
= menu
->GetItems().First();
2895 wxMenuItem
*menuitem
= (wxMenuItem
*)node
->Data();
2896 if (menuitem
->IsSubMenu())
2898 SetInvokingWindow( menuitem
->GetSubMenu(), win
);
2900 node
= node
->Next();
2904 static gint gs_pop_x
= 0;
2905 static gint gs_pop_y
= 0;
2907 static void pop_pos_callback( GtkMenu
*menu
, gint
*x
, gint
*y
, wxWindow
*win
)
2909 win
->ClientToScreen( &gs_pop_x
, &gs_pop_y
);
2914 bool wxWindow::PopupMenu( wxMenu
*menu
, int x
, int y
)
2916 wxCHECK_MSG( m_widget
!= NULL
, FALSE
, _T("invalid window") );
2918 wxCHECK_MSG( menu
!= NULL
, FALSE
, _T("invalid popup-menu") );
2920 SetInvokingWindow( menu
, this );
2928 GTK_MENU(menu
->m_menu
),
2929 (GtkWidget
*) NULL
, // parent menu shell
2930 (GtkWidget
*) NULL
, // parent menu item
2931 (GtkMenuPositionFunc
) pop_pos_callback
,
2932 (gpointer
) this, // client data
2933 0, // button used to activate it
2934 0 //gs_timeLastClick // the time of activation
2939 #if wxUSE_DRAG_AND_DROP
2941 void wxWindow::SetDropTarget( wxDropTarget
*dropTarget
)
2943 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
2945 GtkWidget
*dnd_widget
= GetConnectWidget();
2947 if (m_dropTarget
) m_dropTarget
->UnregisterWidget( dnd_widget
);
2949 if (m_dropTarget
) delete m_dropTarget
;
2950 m_dropTarget
= dropTarget
;
2952 if (m_dropTarget
) m_dropTarget
->RegisterWidget( dnd_widget
);
2955 wxDropTarget
*wxWindow::GetDropTarget() const
2957 return m_dropTarget
;
2962 GtkWidget
* wxWindow::GetConnectWidget()
2964 GtkWidget
*connect_widget
= m_widget
;
2965 if (m_wxwindow
) connect_widget
= m_wxwindow
;
2967 return connect_widget
;
2970 bool wxWindow::IsOwnGtkWindow( GdkWindow
*window
)
2972 if (m_wxwindow
) return (window
== m_wxwindow
->window
);
2973 return (window
== m_widget
->window
);
2976 void wxWindow::SetFont( const wxFont
&font
)
2978 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
2980 if (m_font
== font
) return;
2982 if (((wxFont
*)&font
)->Ok())
2985 m_font
= *wxSWISS_FONT
;
2987 wxColour sysbg
= wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE
);
2988 if (sysbg
.Red() == m_backgroundColour
.Red() &&
2989 sysbg
.Green() == m_backgroundColour
.Green() &&
2990 sysbg
.Blue() == m_backgroundColour
.Blue())
2992 m_backgroundColour
= wxNullColour
;
2994 m_backgroundColour
= sysbg
;
3002 void wxWindow::SetWindowStyleFlag( long flag
)
3004 m_windowStyle
= flag
;
3007 long wxWindow::GetWindowStyleFlag() const
3009 return m_windowStyle
;
3012 void wxWindow::CaptureMouse()
3014 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
3016 wxCHECK_RET( g_capturing
== FALSE
, _T("CaptureMouse called twice") );
3018 if (!m_widget
->window
) return;
3020 GtkWidget
*connect_widget
= GetConnectWidget();
3021 gtk_grab_add( connect_widget
);
3022 gdk_pointer_grab( connect_widget
->window
, FALSE
,
3024 (GDK_BUTTON_PRESS_MASK
|
3025 GDK_BUTTON_RELEASE_MASK
|
3026 GDK_POINTER_MOTION_MASK
),
3033 void wxWindow::ReleaseMouse()
3035 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
3037 wxCHECK_RET( g_capturing
== TRUE
, _T("ReleaseMouse called twice") );
3039 if (!m_widget
->window
) return;
3041 GtkWidget
*connect_widget
= GetConnectWidget();
3042 gtk_grab_remove( connect_widget
);
3043 gdk_pointer_ungrab ( GDK_CURRENT_TIME
);
3044 g_capturing
= FALSE
;
3047 void wxWindow::SetTitle( const wxString
&WXUNUSED(title
) )
3051 wxString
wxWindow::GetTitle() const
3053 return (wxString
&)m_windowName
;
3056 wxString
wxWindow::GetLabel() const
3061 void wxWindow::SetName( const wxString
&name
)
3063 m_windowName
= name
;
3066 wxString
wxWindow::GetName() const
3068 return (wxString
&)m_windowName
;
3071 bool wxWindow::IsShown() const
3076 bool wxWindow::IsRetained()
3081 wxWindow
*wxWindow::FindWindow( long id
)
3083 if (id
== m_windowId
) return this;
3084 wxNode
*node
= m_children
.First();
3087 wxWindow
*child
= (wxWindow
*)node
->Data();
3088 wxWindow
*res
= child
->FindWindow( id
);
3089 if (res
) return res
;
3090 node
= node
->Next();
3092 return (wxWindow
*) NULL
;
3095 wxWindow
*wxWindow::FindWindow( const wxString
& name
)
3097 if (name
== m_windowName
) return this;
3098 wxNode
*node
= m_children
.First();
3101 wxWindow
*child
= (wxWindow
*)node
->Data();
3102 wxWindow
*res
= child
->FindWindow( name
);
3103 if (res
) return res
;
3104 node
= node
->Next();
3106 return (wxWindow
*) NULL
;
3109 void wxWindow::SetScrollbar( int orient
, int pos
, int thumbVisible
,
3110 int range
, bool refresh
)
3112 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
3114 wxCHECK_RET( m_wxwindow
!= NULL
, _T("window needs client area for scrolling") );
3116 m_hasScrolling
= TRUE
;
3118 if (orient
== wxHORIZONTAL
)
3120 float fpos
= (float)pos
;
3121 float frange
= (float)range
;
3122 float fthumb
= (float)thumbVisible
;
3123 if (fpos
> frange
-fthumb
) fpos
= frange
-fthumb
;
3124 if (fpos
< 0.0) fpos
= 0.0;
3126 if ((fabs(frange
-m_hAdjust
->upper
) < 0.2) &&
3127 (fabs(fthumb
-m_hAdjust
->page_size
) < 0.2))
3129 SetScrollPos( orient
, pos
, refresh
);
3133 m_oldHorizontalPos
= fpos
;
3135 m_hAdjust
->lower
= 0.0;
3136 m_hAdjust
->upper
= frange
;
3137 m_hAdjust
->value
= fpos
;
3138 m_hAdjust
->step_increment
= 1.0;
3139 m_hAdjust
->page_increment
= (float)(wxMax(fthumb
,0));
3140 m_hAdjust
->page_size
= fthumb
;
3144 float fpos
= (float)pos
;
3145 float frange
= (float)range
;
3146 float fthumb
= (float)thumbVisible
;
3147 if (fpos
> frange
-fthumb
) fpos
= frange
-fthumb
;
3148 if (fpos
< 0.0) fpos
= 0.0;
3150 if ((fabs(frange
-m_vAdjust
->upper
) < 0.2) &&
3151 (fabs(fthumb
-m_vAdjust
->page_size
) < 0.2))
3153 SetScrollPos( orient
, pos
, refresh
);
3157 m_oldVerticalPos
= fpos
;
3159 m_vAdjust
->lower
= 0.0;
3160 m_vAdjust
->upper
= frange
;
3161 m_vAdjust
->value
= fpos
;
3162 m_vAdjust
->step_increment
= 1.0;
3163 m_vAdjust
->page_increment
= (float)(wxMax(fthumb
,0));
3164 m_vAdjust
->page_size
= fthumb
;
3169 if (orient
== wxHORIZONTAL
)
3170 gtk_signal_emit_by_name( GTK_OBJECT(m_hAdjust
), "changed" );
3172 gtk_signal_emit_by_name( GTK_OBJECT(m_vAdjust
), "changed" );
3174 gtk_widget_set_usize( m_widget
, m_width
, m_height
);
3178 void wxWindow::SetScrollPos( int orient
, int pos
, bool WXUNUSED(refresh
) )
3180 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
3182 wxCHECK_RET( m_wxwindow
!= NULL
, _T("window needs client area for scrolling") );
3184 if (orient
== wxHORIZONTAL
)
3186 float fpos
= (float)pos
;
3187 if (fpos
> m_hAdjust
->upper
- m_hAdjust
->page_size
) fpos
= m_hAdjust
->upper
- m_hAdjust
->page_size
;
3188 if (fpos
< 0.0) fpos
= 0.0;
3189 m_oldHorizontalPos
= fpos
;
3191 if (fabs(fpos
-m_hAdjust
->value
) < 0.2) return;
3192 m_hAdjust
->value
= fpos
;
3196 float fpos
= (float)pos
;
3197 if (fpos
> m_vAdjust
->upper
- m_vAdjust
->page_size
) fpos
= m_vAdjust
->upper
- m_vAdjust
->page_size
;
3198 if (fpos
< 0.0) fpos
= 0.0;
3199 m_oldVerticalPos
= fpos
;
3201 if (fabs(fpos
-m_vAdjust
->value
) < 0.2) return;
3202 m_vAdjust
->value
= fpos
;
3207 if (m_wxwindow
->window
)
3209 if (orient
== wxHORIZONTAL
)
3210 gtk_signal_emit_by_name( GTK_OBJECT(m_hAdjust
), "value_changed" );
3212 gtk_signal_emit_by_name( GTK_OBJECT(m_vAdjust
), "value_changed" );
3217 int wxWindow::GetScrollThumb( int orient
) const
3219 wxCHECK_MSG( m_widget
!= NULL
, 0, _T("invalid window") );
3221 wxCHECK_MSG( m_wxwindow
!= NULL
, 0, _T("window needs client area for scrolling") );
3223 if (orient
== wxHORIZONTAL
)
3224 return (int)(m_hAdjust
->page_size
+0.5);
3226 return (int)(m_vAdjust
->page_size
+0.5);
3229 int wxWindow::GetScrollPos( int orient
) const
3231 wxCHECK_MSG( m_widget
!= NULL
, 0, _T("invalid window") );
3233 wxCHECK_MSG( m_wxwindow
!= NULL
, 0, _T("window needs client area for scrolling") );
3235 if (orient
== wxHORIZONTAL
)
3236 return (int)(m_hAdjust
->value
+0.5);
3238 return (int)(m_vAdjust
->value
+0.5);
3241 int wxWindow::GetScrollRange( int orient
) const
3243 wxCHECK_MSG( m_widget
!= NULL
, 0, _T("invalid window") );
3245 wxCHECK_MSG( m_wxwindow
!= NULL
, 0, _T("window needs client area for scrolling") );
3247 if (orient
== wxHORIZONTAL
)
3248 return (int)(m_hAdjust
->upper
+0.5);
3250 return (int)(m_vAdjust
->upper
+0.5);
3253 void wxWindow::ScrollWindow( int dx
, int dy
, const wxRect
* WXUNUSED(rect
) )
3255 wxCHECK_RET( m_widget
!= NULL
, _T("invalid window") );
3257 wxCHECK_RET( m_wxwindow
!= NULL
, _T("window needs client area for scrolling") );
3259 wxNode
*node
= m_children
.First();
3262 wxWindow
*child
= (wxWindow
*) node
->Data();
3263 child
->Move( child
->m_x
+ dx
, child
->m_y
+ dy
);
3264 node
= node
->Next();
3269 GetClientSize( &cw
, &ch
);
3271 int w
= cw
- abs(dx
);
3272 int h
= ch
- abs(dy
);
3273 if ((h
< 0) || (w
< 0))
3280 if (dx
< 0) s_x
= -dx
;
3281 if (dy
< 0) s_y
= -dy
;
3284 if (dx
> 0) d_x
= dx
;
3285 if (dy
> 0) d_y
= dy
;
3289 m_scrollGC
= gdk_gc_new( m_wxwindow
->window
);
3290 gdk_gc_set_exposures( m_scrollGC
, TRUE
);
3293 gdk_window_copy_area( m_wxwindow
->window
, m_scrollGC
, d_x
, d_y
,
3294 m_wxwindow
->window
, s_x
, s_y
, w
, h
);
3297 if (dx
< 0) rect
.x
= cw
+dx
; else rect
.x
= 0;
3298 if (dy
< 0) rect
.y
= ch
+dy
; else rect
.y
= 0;
3299 if (dy
!= 0) rect
.width
= cw
; else rect
.width
= abs(dx
);
3300 if (dx
!= 0) rect
.height
= ch
; else rect
.height
= abs(dy
);
3302 Refresh( TRUE
, &rect
);
3305 //-------------------------------------------------------------------------------------
3307 //-------------------------------------------------------------------------------------
3309 wxLayoutConstraints
*wxWindow::GetConstraints() const
3311 return m_constraints
;
3314 void wxWindow::SetConstraints( wxLayoutConstraints
*constraints
)
3318 UnsetConstraints(m_constraints
);
3319 delete m_constraints
;
3321 m_constraints
= constraints
;
3324 // Make sure other windows know they're part of a 'meaningful relationship'
3325 if (m_constraints
->left
.GetOtherWindow() && (m_constraints
->left
.GetOtherWindow() != this))
3326 m_constraints
->left
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3327 if (m_constraints
->top
.GetOtherWindow() && (m_constraints
->top
.GetOtherWindow() != this))
3328 m_constraints
->top
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3329 if (m_constraints
->right
.GetOtherWindow() && (m_constraints
->right
.GetOtherWindow() != this))
3330 m_constraints
->right
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3331 if (m_constraints
->bottom
.GetOtherWindow() && (m_constraints
->bottom
.GetOtherWindow() != this))
3332 m_constraints
->bottom
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3333 if (m_constraints
->width
.GetOtherWindow() && (m_constraints
->width
.GetOtherWindow() != this))
3334 m_constraints
->width
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3335 if (m_constraints
->height
.GetOtherWindow() && (m_constraints
->height
.GetOtherWindow() != this))
3336 m_constraints
->height
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3337 if (m_constraints
->centreX
.GetOtherWindow() && (m_constraints
->centreX
.GetOtherWindow() != this))
3338 m_constraints
->centreX
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3339 if (m_constraints
->centreY
.GetOtherWindow() && (m_constraints
->centreY
.GetOtherWindow() != this))
3340 m_constraints
->centreY
.GetOtherWindow()->AddConstraintReference((wxWindow
*)this);
3346 void wxWindow::SetAutoLayout( bool autoLayout
)
3348 m_autoLayout
= autoLayout
;
3351 bool wxWindow::GetAutoLayout() const
3353 return m_autoLayout
;
3356 wxSizer
*wxWindow::GetSizer() const
3358 return m_windowSizer
;
3361 void wxWindow::SetSizerParent( wxWindow
*win
)
3363 m_sizerParent
= win
;
3366 wxWindow
*wxWindow::GetSizerParent() const
3368 return m_sizerParent
;
3371 // This removes any dangling pointers to this window
3372 // in other windows' constraintsInvolvedIn lists.
3373 void wxWindow::UnsetConstraints(wxLayoutConstraints
*c
)
3377 if (c
->left
.GetOtherWindow() && (c
->top
.GetOtherWindow() != this))
3378 c
->left
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3379 if (c
->top
.GetOtherWindow() && (c
->top
.GetOtherWindow() != this))
3380 c
->top
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3381 if (c
->right
.GetOtherWindow() && (c
->right
.GetOtherWindow() != this))
3382 c
->right
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3383 if (c
->bottom
.GetOtherWindow() && (c
->bottom
.GetOtherWindow() != this))
3384 c
->bottom
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3385 if (c
->width
.GetOtherWindow() && (c
->width
.GetOtherWindow() != this))
3386 c
->width
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3387 if (c
->height
.GetOtherWindow() && (c
->height
.GetOtherWindow() != this))
3388 c
->height
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3389 if (c
->centreX
.GetOtherWindow() && (c
->centreX
.GetOtherWindow() != this))
3390 c
->centreX
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3391 if (c
->centreY
.GetOtherWindow() && (c
->centreY
.GetOtherWindow() != this))
3392 c
->centreY
.GetOtherWindow()->RemoveConstraintReference((wxWindow
*)this);
3396 // Back-pointer to other windows we're involved with, so if we delete
3397 // this window, we must delete any constraints we're involved with.
3398 void wxWindow::AddConstraintReference(wxWindow
*otherWin
)
3400 if (!m_constraintsInvolvedIn
)
3401 m_constraintsInvolvedIn
= new wxList
;
3402 if (!m_constraintsInvolvedIn
->Member(otherWin
))
3403 m_constraintsInvolvedIn
->Append(otherWin
);
3406 // REMOVE back-pointer to other windows we're involved with.
3407 void wxWindow::RemoveConstraintReference(wxWindow
*otherWin
)
3409 if (m_constraintsInvolvedIn
)
3410 m_constraintsInvolvedIn
->DeleteObject(otherWin
);
3413 // Reset any constraints that mention this window
3414 void wxWindow::DeleteRelatedConstraints()
3416 if (m_constraintsInvolvedIn
)
3418 wxNode
*node
= m_constraintsInvolvedIn
->First();
3421 wxWindow
*win
= (wxWindow
*)node
->Data();
3422 wxNode
*next
= node
->Next();
3423 wxLayoutConstraints
*constr
= win
->GetConstraints();
3425 // Reset any constraints involving this window
3428 constr
->left
.ResetIfWin((wxWindow
*)this);
3429 constr
->top
.ResetIfWin((wxWindow
*)this);
3430 constr
->right
.ResetIfWin((wxWindow
*)this);
3431 constr
->bottom
.ResetIfWin((wxWindow
*)this);
3432 constr
->width
.ResetIfWin((wxWindow
*)this);
3433 constr
->height
.ResetIfWin((wxWindow
*)this);
3434 constr
->centreX
.ResetIfWin((wxWindow
*)this);
3435 constr
->centreY
.ResetIfWin((wxWindow
*)this);
3440 delete m_constraintsInvolvedIn
;
3441 m_constraintsInvolvedIn
= (wxList
*) NULL
;
3445 void wxWindow::SetSizer(wxSizer
*sizer
)
3447 m_windowSizer
= sizer
;
3449 sizer
->SetSizerParent((wxWindow
*)this);
3456 bool wxWindow::Layout()
3458 if (GetConstraints())
3461 GetClientSize(&w
, &h
);
3462 GetConstraints()->width
.SetValue(w
);
3463 GetConstraints()->height
.SetValue(h
);
3466 // If top level (one sizer), evaluate the sizer's constraints.
3470 GetSizer()->ResetConstraints(); // Mark all constraints as unevaluated
3471 GetSizer()->LayoutPhase1(&noChanges
);
3472 GetSizer()->LayoutPhase2(&noChanges
);
3473 GetSizer()->SetConstraintSizes(); // Recursively set the real window sizes
3478 // Otherwise, evaluate child constraints
3479 ResetConstraints(); // Mark all constraints as unevaluated
3480 DoPhase(1); // Just one phase need if no sizers involved
3482 SetConstraintSizes(); // Recursively set the real window sizes
3488 // Do a phase of evaluating constraints:
3489 // the default behaviour. wxSizers may do a similar
3490 // thing, but also impose their own 'constraints'
3491 // and order the evaluation differently.
3492 bool wxWindow::LayoutPhase1(int *noChanges
)
3494 wxLayoutConstraints
*constr
= GetConstraints();
3497 return constr
->SatisfyConstraints((wxWindow
*)this, noChanges
);
3503 bool wxWindow::LayoutPhase2(int *noChanges
)
3513 // Do a phase of evaluating child constraints
3514 bool wxWindow::DoPhase(int phase
)
3516 int noIterations
= 0;
3517 int maxIterations
= 500;
3521 while ((noChanges
> 0) && (noIterations
< maxIterations
))
3525 wxNode
*node
= m_children
.First();
3528 wxWindow
*child
= (wxWindow
*)node
->Data();
3529 if (!child
->IsKindOf(CLASSINFO(wxFrame
)) && !child
->IsKindOf(CLASSINFO(wxDialog
)))
3531 wxLayoutConstraints
*constr
= child
->GetConstraints();
3534 if (succeeded
.Member(child
))
3539 int tempNoChanges
= 0;
3540 bool success
= ( (phase
== 1) ? child
->LayoutPhase1(&tempNoChanges
) : child
->LayoutPhase2(&tempNoChanges
) ) ;
3541 noChanges
+= tempNoChanges
;
3544 succeeded
.Append(child
);
3549 node
= node
->Next();
3556 void wxWindow::ResetConstraints()
3558 wxLayoutConstraints
*constr
= GetConstraints();
3561 constr
->left
.SetDone(FALSE
);
3562 constr
->top
.SetDone(FALSE
);
3563 constr
->right
.SetDone(FALSE
);
3564 constr
->bottom
.SetDone(FALSE
);
3565 constr
->width
.SetDone(FALSE
);
3566 constr
->height
.SetDone(FALSE
);
3567 constr
->centreX
.SetDone(FALSE
);
3568 constr
->centreY
.SetDone(FALSE
);
3570 wxNode
*node
= m_children
.First();
3573 wxWindow
*win
= (wxWindow
*)node
->Data();
3574 if (!win
->IsKindOf(CLASSINFO(wxFrame
)) && !win
->IsKindOf(CLASSINFO(wxDialog
)))
3575 win
->ResetConstraints();
3576 node
= node
->Next();
3580 // Need to distinguish between setting the 'fake' size for
3581 // windows and sizers, and setting the real values.
3582 void wxWindow::SetConstraintSizes(bool recurse
)
3584 wxLayoutConstraints
*constr
= GetConstraints();
3585 if (constr
&& constr
->left
.GetDone() && constr
->right
.GetDone() &&
3586 constr
->width
.GetDone() && constr
->height
.GetDone())
3588 int x
= constr
->left
.GetValue();
3589 int y
= constr
->top
.GetValue();
3590 int w
= constr
->width
.GetValue();
3591 int h
= constr
->height
.GetValue();
3593 // If we don't want to resize this window, just move it...
3594 if ((constr
->width
.GetRelationship() != wxAsIs
) ||
3595 (constr
->height
.GetRelationship() != wxAsIs
))
3597 // Calls Layout() recursively. AAAGH. How can we stop that.
3598 // Simply take Layout() out of non-top level OnSizes.
3599 SizerSetSize(x
, y
, w
, h
);
3608 wxChar
*windowClass
= this->GetClassInfo()->GetClassName();
3611 if (GetName() == _T(""))
3612 winName
= _T("unnamed");
3614 winName
= GetName();
3615 wxLogDebug( _T("Constraint(s) not satisfied for window of type %s, name %s:\n"),
3616 (const wxChar
*)windowClass
,
3617 (const wxChar
*)winName
);
3618 if (!constr
->left
.GetDone()) wxLogDebug( _T(" unsatisfied 'left' constraint.\n") );
3619 if (!constr
->right
.GetDone()) wxLogDebug( _T(" unsatisfied 'right' constraint.\n") );
3620 if (!constr
->width
.GetDone()) wxLogDebug( _T(" unsatisfied 'width' constraint.\n") );
3621 if (!constr
->height
.GetDone()) wxLogDebug( _T(" unsatisfied 'height' constraint.\n") );
3622 wxLogDebug( _T("Please check constraints: try adding AsIs() constraints.\n") );
3627 wxNode
*node
= m_children
.First();
3630 wxWindow
*win
= (wxWindow
*)node
->Data();
3631 if (!win
->IsKindOf(CLASSINFO(wxFrame
)) && !win
->IsKindOf(CLASSINFO(wxDialog
)))
3632 win
->SetConstraintSizes();
3633 node
= node
->Next();
3638 // This assumes that all sizers are 'on' the same
3639 // window, i.e. the parent of this window.
3640 void wxWindow::TransformSizerToActual(int *x
, int *y
) const
3642 if (!m_sizerParent
|| m_sizerParent
->IsKindOf(CLASSINFO(wxDialog
)) ||
3643 m_sizerParent
->IsKindOf(CLASSINFO(wxFrame
)) )
3647 m_sizerParent
->GetPosition(&xp
, &yp
);
3648 m_sizerParent
->TransformSizerToActual(&xp
, &yp
);
3653 void wxWindow::SizerSetSize(int x
, int y
, int w
, int h
)
3657 TransformSizerToActual(&xx
, &yy
);
3658 SetSize(xx
, yy
, w
, h
);
3661 void wxWindow::SizerMove(int x
, int y
)
3665 TransformSizerToActual(&xx
, &yy
);
3669 // Only set the size/position of the constraint (if any)
3670 void wxWindow::SetSizeConstraint(int x
, int y
, int w
, int h
)
3672 wxLayoutConstraints
*constr
= GetConstraints();
3677 constr
->left
.SetValue(x
);
3678 constr
->left
.SetDone(TRUE
);
3682 constr
->top
.SetValue(y
);
3683 constr
->top
.SetDone(TRUE
);
3687 constr
->width
.SetValue(w
);
3688 constr
->width
.SetDone(TRUE
);
3692 constr
->height
.SetValue(h
);
3693 constr
->height
.SetDone(TRUE
);
3698 void wxWindow::MoveConstraint(int x
, int y
)
3700 wxLayoutConstraints
*constr
= GetConstraints();
3705 constr
->left
.SetValue(x
);
3706 constr
->left
.SetDone(TRUE
);
3710 constr
->top
.SetValue(y
);
3711 constr
->top
.SetDone(TRUE
);
3716 void wxWindow::GetSizeConstraint(int *w
, int *h
) const
3718 wxLayoutConstraints
*constr
= GetConstraints();
3721 *w
= constr
->width
.GetValue();
3722 *h
= constr
->height
.GetValue();
3728 void wxWindow::GetClientSizeConstraint(int *w
, int *h
) const
3730 wxLayoutConstraints
*constr
= GetConstraints();
3733 *w
= constr
->width
.GetValue();
3734 *h
= constr
->height
.GetValue();
3737 GetClientSize(w
, h
);
3740 void wxWindow::GetPositionConstraint(int *x
, int *y
) const
3742 wxLayoutConstraints
*constr
= GetConstraints();
3745 *x
= constr
->left
.GetValue();
3746 *y
= constr
->top
.GetValue();