1 ///////////////////////////////////////////////////////////////////////////////
2 // Name: src/gtk/private.cpp
3 // Purpose: implementation of wxGTK private functions
4 // Author: Marcin Malich
5 // Modified by:
6 // Created: 28.06.2008
7 // Copyright: (c) 2008 Marcin Malich <me@malcom.pl>
8 // Licence: wxWindows licence
9 ///////////////////////////////////////////////////////////////////////////////
10
11 // ============================================================================
12 // declarations
13 // ============================================================================
14
15 // ----------------------------------------------------------------------------
16 // headers
17 // ----------------------------------------------------------------------------
18
19 // for compilers that support precompilation, includes "wx.h".
20 #include "wx/wxprec.h"
21
22 #ifdef __BORLANDC__
23 #pragma hdrstop
24 #endif
25
26 #ifndef WX_PRECOMP
27 #include "wx/module.h"
28 #endif
29
30 #include <gtk/gtk.h>
31 #include "wx/gtk/private.h"
32
33 // ----------------------------------------------------------------------------
34 // wxGTKPrivate functions implementation
35 // ----------------------------------------------------------------------------
36
37 namespace wxGTKPrivate
38 {
39
40 static GtkWidget *gs_container = NULL;
41
GetContainer()42 static GtkContainer* GetContainer()
43 {
44 if ( gs_container == NULL )
45 {
46 GtkWidget* window = gtk_window_new(GTK_WINDOW_POPUP);
47 gs_container = gtk_fixed_new();
48 gtk_container_add(GTK_CONTAINER(window), gs_container);
49 }
50 return GTK_CONTAINER(gs_container);
51 }
52
GetButtonWidget()53 GtkWidget *GetButtonWidget()
54 {
55 static GtkWidget *s_button = NULL;
56
57 if ( !s_button )
58 {
59 s_button = gtk_button_new();
60 g_object_add_weak_pointer(G_OBJECT(s_button), (void**)&s_button);
61 gtk_container_add(GetContainer(), s_button);
62 gtk_widget_realize(s_button);
63 }
64
65 return s_button;
66 }
67
GetNotebookWidget()68 GtkWidget *GetNotebookWidget()
69 {
70 static GtkWidget *s_notebook = NULL;
71
72 if ( !s_notebook )
73 {
74 s_notebook = gtk_notebook_new();
75 g_object_add_weak_pointer(G_OBJECT(s_notebook), (void**)&s_notebook);
76 gtk_container_add(GetContainer(), s_notebook);
77 gtk_widget_realize(s_notebook);
78 }
79
80 return s_notebook;
81 }
82
GetCheckButtonWidget()83 GtkWidget *GetCheckButtonWidget()
84 {
85 static GtkWidget *s_button = NULL;
86
87 if ( !s_button )
88 {
89 s_button = gtk_check_button_new();
90 g_object_add_weak_pointer(G_OBJECT(s_button), (void**)&s_button);
91 gtk_container_add(GetContainer(), s_button);
92 gtk_widget_realize(s_button);
93 }
94
95 return s_button;
96 }
97
GetComboBoxWidget()98 GtkWidget * GetComboBoxWidget()
99 {
100 static GtkWidget *s_button = NULL;
101
102 if ( !s_button )
103 {
104 s_button = gtk_combo_box_new();
105 g_object_add_weak_pointer(G_OBJECT(s_button), (void**)&s_button);
106 gtk_container_add(GetContainer(), s_button);
107 gtk_widget_realize( s_button );
108 }
109
110 return s_button;
111 }
112
113
GetEntryWidget()114 GtkWidget *GetEntryWidget()
115 {
116 static GtkWidget *s_entry = NULL;
117
118 if ( !s_entry )
119 {
120 s_entry = gtk_entry_new();
121 g_object_add_weak_pointer(G_OBJECT(s_entry), (void**)&s_entry);
122 gtk_container_add(GetContainer(), s_entry);
123 gtk_widget_realize(s_entry);
124 }
125
126 return s_entry;
127 }
128
129 // This one just gets the button used by the column header. Although it's
130 // still a gtk_button the themes will typically differentiate and draw them
131 // differently if the button is in a treeview.
132 static GtkWidget *s_first_button = NULL;
133 static GtkWidget *s_other_button = NULL;
134 static GtkWidget *s_last_button = NULL;
135
CreateHeaderButtons()136 static void CreateHeaderButtons()
137 {
138 // Get the dummy tree widget, give it a column, and then use the
139 // widget in the column header for the rendering code.
140 GtkWidget* treewidget = GetTreeWidget();
141
142 GtkTreeViewColumn *column = gtk_tree_view_column_new();
143 gtk_tree_view_append_column(GTK_TREE_VIEW(treewidget), column);
144 #ifdef __WXGTK3__
145 s_first_button = gtk_tree_view_column_get_button(column);
146 #else
147 s_first_button = column->button;
148 #endif
149 wxASSERT(s_first_button);
150 g_object_add_weak_pointer(G_OBJECT(s_first_button), (void**)&s_first_button);
151
152 column = gtk_tree_view_column_new();
153 gtk_tree_view_append_column(GTK_TREE_VIEW(treewidget), column);
154 #ifdef __WXGTK3__
155 s_other_button = gtk_tree_view_column_get_button(column);
156 #else
157 s_other_button = column->button;
158 #endif
159 g_object_add_weak_pointer(G_OBJECT(s_other_button), (void**)&s_other_button);
160
161 column = gtk_tree_view_column_new();
162 gtk_tree_view_append_column(GTK_TREE_VIEW(treewidget), column);
163 #ifdef __WXGTK3__
164 s_last_button = gtk_tree_view_column_get_button(column);
165 #else
166 s_last_button = column->button;
167 #endif
168 g_object_add_weak_pointer(G_OBJECT(s_last_button), (void**)&s_last_button);
169 }
170
GetHeaderButtonWidgetFirst()171 GtkWidget *GetHeaderButtonWidgetFirst()
172 {
173 if (!s_first_button)
174 CreateHeaderButtons();
175
176 return s_first_button;
177 }
178
GetHeaderButtonWidgetLast()179 GtkWidget *GetHeaderButtonWidgetLast()
180 {
181 if (!s_last_button)
182 CreateHeaderButtons();
183
184 return s_last_button;
185 }
186
GetHeaderButtonWidget()187 GtkWidget *GetHeaderButtonWidget()
188 {
189 if (!s_other_button)
190 CreateHeaderButtons();
191
192 return s_other_button;
193 }
194
GetRadioButtonWidget()195 GtkWidget * GetRadioButtonWidget()
196 {
197 static GtkWidget *s_button = NULL;
198
199 if ( !s_button )
200 {
201 s_button = gtk_radio_button_new(NULL);
202 g_object_add_weak_pointer(G_OBJECT(s_button), (void**)&s_button);
203 gtk_container_add(GetContainer(), s_button);
204 gtk_widget_realize( s_button );
205 }
206
207 return s_button;
208 }
209
GetSplitterWidget(wxOrientation orient)210 GtkWidget* GetSplitterWidget(wxOrientation orient)
211 {
212 static GtkWidget* widgets[2];
213 const GtkOrientation gtkOrient =
214 orient == wxHORIZONTAL ? GTK_ORIENTATION_HORIZONTAL : GTK_ORIENTATION_VERTICAL;
215 GtkWidget*& widget = widgets[gtkOrient];
216 if (widget == NULL)
217 {
218 #ifdef __WXGTK3__
219 widget = gtk_paned_new(gtkOrient);
220 #else
221 if (orient == wxHORIZONTAL)
222 widget = gtk_hpaned_new();
223 else
224 widget = gtk_vpaned_new();
225 #endif
226 g_object_add_weak_pointer(G_OBJECT(widget), (void**)&widgets[gtkOrient]);
227 gtk_container_add(GetContainer(), widget);
228 gtk_widget_realize(widget);
229 }
230
231 return widget;
232 }
233
GetTextEntryWidget()234 GtkWidget * GetTextEntryWidget()
235 {
236 static GtkWidget *s_button = NULL;
237
238 if ( !s_button )
239 {
240 s_button = gtk_entry_new();
241 g_object_add_weak_pointer(G_OBJECT(s_button), (void**)&s_button);
242 gtk_container_add(GetContainer(), s_button);
243 gtk_widget_realize( s_button );
244 }
245
246 return s_button;
247 }
248
GetTreeWidget()249 GtkWidget *GetTreeWidget()
250 {
251 static GtkWidget *s_tree = NULL;
252
253 if ( !s_tree )
254 {
255 s_tree = gtk_tree_view_new();
256 g_object_add_weak_pointer(G_OBJECT(s_tree), (void**)&s_tree);
257 gtk_container_add(GetContainer(), s_tree);
258 gtk_widget_realize(s_tree);
259 }
260
261 return s_tree;
262 }
263
264 // Module for destroying created widgets
265 class WidgetsCleanupModule : public wxModule
266 {
267 public:
OnInit()268 virtual bool OnInit()
269 {
270 return true;
271 }
272
OnExit()273 virtual void OnExit()
274 {
275 if ( gs_container )
276 {
277 GtkWidget* parent = gtk_widget_get_parent(gs_container);
278 gtk_widget_destroy(parent);
279 gs_container = NULL;
280 }
281 }
282
283 DECLARE_DYNAMIC_CLASS(WidgetsCleanupModule)
284 };
285
286 IMPLEMENT_DYNAMIC_CLASS(WidgetsCleanupModule, wxModule)
287
288 } // wxGTKPrivate namespace
289