]> git.saurik.com Git - wxWidgets.git/blame - src/gtk1/app.cpp
no message
[wxWidgets.git] / src / gtk1 / app.cpp
CommitLineData
c801d85f
KB
1/////////////////////////////////////////////////////////////////////////////
2// Name: app.cpp
3// Purpose:
4// Author: Robert Roebling
32e9da8b 5// Id: $Id$
01111366 6// Copyright: (c) 1998 Robert Roebling, Julian Smart
8bbe427f 7// Licence: wxWindows licence
c801d85f
KB
8/////////////////////////////////////////////////////////////////////////////
9
10#ifdef __GNUG__
11#pragma implementation "app.h"
12#endif
13
14#include "wx/app.h"
15#include "wx/gdicmn.h"
16#include "wx/utils.h"
c801d85f
KB
17#include "wx/intl.h"
18#include "wx/log.h"
46dc76ba 19#include "wx/memory.h"
a3622daa
VZ
20#include "wx/font.h"
21#include "wx/settings.h"
06cfab17 22#if wxUSE_WX_RESOURCES
8d71b555 23#include "wx/resource.h"
f5abe911 24#endif
031b2a7b 25#include "wx/module.h"
4bc67cc5 26#include "wx/image.h"
06cfab17 27#if wxUSE_THREADS
f3855ef0 28#include "wx/thread.h"
ac57418f 29#endif
c801d85f
KB
30#include "unistd.h"
31
83624f79
RR
32#include "glib.h"
33#include "gdk/gdk.h"
34#include "gtk/gtk.h"
35#include "wx/gtk/win_gtk.h"
36
c801d85f
KB
37//-----------------------------------------------------------------------------
38// global data
39//-----------------------------------------------------------------------------
40
c67daf87 41wxApp *wxTheApp = (wxApp *) NULL;
c801d85f
KB
42wxAppInitializerFunction wxApp::m_appInitFn = (wxAppInitializerFunction) NULL;
43
44extern wxList wxPendingDelete;
a3622daa 45extern wxResourceCache *wxTheResourceCache;
c801d85f 46
01111366
RR
47unsigned char g_palette[64*3] =
48{
49 0x0, 0x0, 0x0,
50 0xff, 0xff, 0xff,
51 0xff, 0x0, 0x0,
52 0xff, 0xff, 0x0,
53 0x0, 0xff, 0x0,
54 0x0, 0x0, 0xff,
55 0x0, 0xff, 0xff,
56 0x99, 0x99, 0x99,
57 0xff, 0x88, 0x0,
58 0x88, 0x0, 0x0,
59 0x0, 0x88, 0x88,
60 0x88, 0x88, 0x0,
61 0xff, 0xcc, 0x97,
62 0xbb, 0xbb, 0xbb,
63 0x9f, 0x6b, 0x42,
64 0x55, 0x55, 0x55,
65 0xdd, 0xdd, 0xdd,
66 0x77, 0x77, 0x77,
67 0x33, 0x33, 0x33,
68 0xcc, 0x0, 0x0,
69 0xff, 0x44, 0x0,
70 0xff, 0xcc, 0x0,
71 0xcc, 0xcc, 0x0,
72 0x60, 0x60, 0x0,
73 0x0, 0x43, 0x0,
74 0x0, 0x7f, 0x0,
75 0x0, 0xcc, 0x0,
76 0x0, 0x44, 0x44,
77 0x0, 0x0, 0x44,
78 0x0, 0x0, 0x88,
79 0xef, 0xb1, 0x7b,
80 0xdf, 0x98, 0x5f,
81 0xbf, 0x87, 0x56,
82 0x7f, 0x57, 0x26,
83 0x5f, 0x39, 0xc,
84 0x3f, 0x1c, 0x0,
85 0x21, 0x0, 0x0,
86 0x0, 0x43, 0x87,
87 0x2d, 0x70, 0xaf,
88 0x5a, 0x9e, 0xd7,
89 0x87, 0xcc, 0xff,
90 0xff, 0xe0, 0xba,
91 0x21, 0x43, 0xf,
92 0x3d, 0x5d, 0x25,
93 0x59, 0x78, 0x3a,
94 0x75, 0x93, 0x4f,
95 0x91, 0xae, 0x64,
96 0xad, 0xc8, 0x7a,
e0253070 97 0xf0, 0xa8, 0xef,
01111366
RR
98 0xd0, 0x88, 0xd0,
99 0xaf, 0x66, 0xaf,
100 0x8e, 0x44, 0x8e,
101 0x6d, 0x22, 0x6d,
e0253070 102 0x4b, 0x0, 0x4b,
01111366
RR
103 0xff, 0xc0, 0xbc,
104 0xff, 0x93, 0x91,
105 0xff, 0x66, 0x67,
106 0xd8, 0xf2, 0xbf,
107 0xff, 0xc9, 0x68,
108 0xff, 0x96, 0x67,
109 0xa5, 0x60, 0xff,
110 0x51, 0xff, 0x99,
111 0x3f, 0xa5, 0x63,
112 0x98, 0x90, 0x67
113};
114
c801d85f
KB
115//-----------------------------------------------------------------------------
116// local functions
117//-----------------------------------------------------------------------------
118
119extern void wxFlushResources(void);
120
121//-----------------------------------------------------------------------------
122// global functions
123//-----------------------------------------------------------------------------
124
125void wxExit(void)
126{
ec758a20 127 gtk_main_quit();
ff7b1510 128}
c801d85f
KB
129
130bool wxYield(void)
131{
ec758a20
RR
132 while (gtk_events_pending() > 0) gtk_main_iteration();
133 return TRUE;
ff7b1510 134}
c801d85f
KB
135
136//-----------------------------------------------------------------------------
137// wxApp
138//-----------------------------------------------------------------------------
139
140IMPLEMENT_DYNAMIC_CLASS(wxApp,wxEvtHandler)
141
53010e52
RR
142BEGIN_EVENT_TABLE(wxApp, wxEvtHandler)
143 EVT_IDLE(wxApp::OnIdle)
144END_EVENT_TABLE()
145
c801d85f
KB
146gint wxapp_idle_callback( gpointer WXUNUSED(data) )
147{
ec758a20 148 if (wxTheApp) while (wxTheApp->ProcessIdle()) {}
06cfab17 149#if wxUSE_THREADS
f3855ef0 150 wxMutexGuiLeave();
ac57418f 151#endif
f3855ef0 152 usleep(10000);
06cfab17 153#if wxUSE_THREADS
f3855ef0 154 wxMutexGuiEnter();
ac57418f 155#endif
ec758a20 156 return TRUE;
ff7b1510 157}
c801d85f
KB
158
159wxApp::wxApp()
160{
ec758a20
RR
161 m_idleTag = 0;
162 m_topWindow = (wxWindow *) NULL;
163 m_exitOnFrameDelete = TRUE;
164 wxTheApp = this;
ff7b1510 165}
c801d85f
KB
166
167wxApp::~wxApp(void)
168{
ec758a20 169 gtk_idle_remove( m_idleTag );
ff7b1510 170}
c801d85f
KB
171
172bool wxApp::OnInit(void)
173{
ec758a20 174 return TRUE;
ff7b1510 175}
c801d85f
KB
176
177bool wxApp::OnInitGui(void)
0cf2cb36 178{
ec758a20
RR
179 m_idleTag = gtk_idle_add( wxapp_idle_callback, NULL );
180 return TRUE;
ff7b1510 181}
c801d85f 182
0cf2cb36
RD
183int wxApp::OnRun(void)
184{
ec758a20 185 return MainLoop();
ff7b1510 186}
c801d85f 187
53010e52
RR
188bool wxApp::ProcessIdle(void)
189{
ec758a20
RR
190 wxIdleEvent event;
191 event.SetEventObject( this );
192 ProcessEvent( event );
0cf2cb36 193
ec758a20 194 return event.MoreRequested();
ff7b1510 195}
53010e52
RR
196
197void wxApp::OnIdle( wxIdleEvent &event )
c801d85f 198{
ec758a20 199 static bool inOnIdle = FALSE;
53010e52 200
d524867f 201 /* Avoid recursion (via ProcessEvent default case) */
ec758a20
RR
202 if (inOnIdle)
203 return;
53010e52 204
ec758a20 205 inOnIdle = TRUE;
53010e52 206
d524867f 207 /* 'Garbage' collection of windows deleted with Close(). */
ec758a20 208 DeletePendingObjects();
53010e52 209
d524867f
RR
210 /* flush the logged messages if any */
211 wxLog *log = wxLog::GetActiveTarget();
212 if (log != NULL && log->HasPendingMessages())
213 log->Flush();
53010e52 214
d524867f 215 /* Send OnIdle events to all windows */
ec758a20 216 bool needMore = SendIdleEvents();
53010e52 217
ec758a20
RR
218 if (needMore)
219 event.RequestMore(TRUE);
53010e52 220
ec758a20 221 inOnIdle = FALSE;
ff7b1510 222}
53010e52
RR
223
224bool wxApp::SendIdleEvents(void)
225{
226 bool needMore = FALSE;
e0253070 227
ec758a20
RR
228 wxNode* node = wxTopLevelWindows.First();
229 while (node)
230 {
f3855ef0
RR
231 wxWindow* win = (wxWindow*) node->Data();
232 if (SendIdleEvents(win))
53010e52 233 needMore = TRUE;
ec758a20
RR
234 node = node->Next();
235 }
53010e52 236 return needMore;
ff7b1510 237}
53010e52
RR
238
239bool wxApp::SendIdleEvents( wxWindow* win )
240{
241 bool needMore = FALSE;
242
8bbe427f
VZ
243 wxIdleEvent event;
244 event.SetEventObject(win);
245 win->ProcessEvent(event);
53010e52
RR
246
247 if (event.MoreRequested())
248 needMore = TRUE;
249
8bbe427f
VZ
250 wxNode* node = win->GetChildren().First();
251 while (node)
252 {
253 wxWindow* win = (wxWindow*) node->Data();
254 if (SendIdleEvents(win))
53010e52
RR
255 needMore = TRUE;
256
8bbe427f
VZ
257 node = node->Next();
258 }
53010e52 259 return needMore ;
ff7b1510 260}
c801d85f
KB
261
262int wxApp::OnExit(void)
263{
ec758a20 264 return 0;
ff7b1510 265}
c801d85f
KB
266
267int wxApp::MainLoop(void)
268{
ec758a20
RR
269 gtk_main();
270 return 0;
ff7b1510 271}
c801d85f
KB
272
273void wxApp::ExitMainLoop(void)
274{
ec758a20 275 gtk_main_quit();
ff7b1510 276}
c801d85f
KB
277
278bool wxApp::Initialized(void)
279{
ec758a20 280 return m_initialized;
ff7b1510 281}
c801d85f 282
0cf2cb36 283bool wxApp::Pending(void)
c801d85f 284{
ec758a20 285 return FALSE;
ff7b1510 286}
c801d85f 287
0cf2cb36 288void wxApp::Dispatch(void)
c801d85f 289{
ff7b1510 290}
c801d85f
KB
291
292void wxApp::DeletePendingObjects(void)
293{
ec758a20
RR
294 wxNode *node = wxPendingDelete.First();
295 while (node)
296 {
297 wxObject *obj = (wxObject *)node->Data();
0cf2cb36 298
ec758a20 299 delete obj;
c801d85f 300
ec758a20
RR
301 if (wxPendingDelete.Member(obj))
302 delete node;
c801d85f 303
ec758a20
RR
304 node = wxPendingDelete.First();
305 }
ff7b1510 306}
c801d85f
KB
307
308wxWindow *wxApp::GetTopWindow(void)
309{
ec758a20
RR
310 if (m_topWindow) return m_topWindow;
311 wxNode *node = wxTopLevelWindows.First();
312 if (!node) return (wxWindow *) NULL;
313 return (wxWindow*)node->Data();
ff7b1510 314}
c801d85f
KB
315
316void wxApp::SetTopWindow( wxWindow *win )
317{
ec758a20 318 m_topWindow = win;
ff7b1510 319}
c801d85f
KB
320
321void wxApp::CommonInit(void)
322{
323
324/*
47d67540 325#if wxUSE_RESOURCES
c801d85f
KB
326 (void) wxGetResource("wxWindows", "OsVersion", &wxOsVersion);
327#endif
328*/
a3622daa 329 wxSystemSettings::Init();
f5abe911 330
a3622daa
VZ
331 wxTheFontNameDirectory = new wxFontNameDirectory;
332 wxTheFontNameDirectory->Initialize();
c801d85f
KB
333
334 wxTheColourDatabase = new wxColourDatabase(wxKEY_STRING);
335 wxTheColourDatabase->Initialize();
a3622daa
VZ
336
337 wxInitializeStockLists();
c801d85f
KB
338 wxInitializeStockObjects();
339
06cfab17 340#if wxUSE_WX_RESOURCES
f5abe911
RR
341 wxTheResourceCache = new wxResourceCache(wxKEY_STRING);
342
8d71b555 343 wxInitializeResourceSystem();
f5abe911 344#endif
0cf2cb36 345
fd0eed64 346 wxImage::InitStandardHandlers();
e0253070 347
fd0eed64 348// g_globalCursor = new wxCursor;
ff7b1510 349}
c801d85f
KB
350
351void wxApp::CommonCleanUp(void)
352{
ec758a20
RR
353 wxDELETE(wxTheColourDatabase);
354 wxDELETE(wxTheFontNameDirectory);
355 wxDeleteStockObjects();
0cf2cb36 356
06cfab17 357#if wxUSE_WX_RESOURCES
ec758a20 358 wxFlushResources();
a3622daa 359
ec758a20 360 wxDELETE(wxTheResourceCache);
f5abe911
RR
361
362 wxCleanUpResourceSystem();
363#endif
a3622daa 364
ec758a20 365 wxDeleteStockLists();
a3622daa 366
ec758a20 367 wxImage::CleanUpHandlers();
0cf2cb36 368
ec758a20 369 wxSystemSettings::Done();
ff7b1510 370}
0cf2cb36 371
c801d85f
KB
372wxLog *wxApp::CreateLogTarget()
373{
374 return new wxLogGui;
375}
376
377//-----------------------------------------------------------------------------
378// wxEntry
379//-----------------------------------------------------------------------------
380
381int wxEntry( int argc, char *argv[] )
382{
ec758a20 383 wxBuffer = new char[BUFSIZ + 512];
c801d85f 384
ec758a20 385 wxClassInfo::InitializeClasses();
0cf2cb36 386
0cf2cb36 387
ec758a20 388 if (!wxTheApp)
c801d85f 389 {
ec758a20
RR
390 if (!wxApp::GetInitializerFunction())
391 {
392 printf( "wxWindows error: No initializer - use IMPLEMENT_APP macro.\n" );
393 return 0;
394 }
0cf2cb36 395
ec758a20 396 wxAppInitializerFunction app_ini = wxApp::GetInitializerFunction();
0cf2cb36 397
ec758a20 398 wxObject *test_app = app_ini();
0cf2cb36 399
ec758a20
RR
400 wxTheApp = (wxApp*) test_app;
401 }
0cf2cb36 402
ec758a20
RR
403 if (!wxTheApp)
404 {
405 printf( "wxWindows error: wxTheApp == NULL\n" );
406 return 0;
407 }
c801d85f 408
ec758a20
RR
409 wxTheApp->argc = argc;
410 wxTheApp->argv = argv;
0cf2cb36 411
ec758a20
RR
412 char name[200];
413 strcpy( name, argv[0] );
414 strcpy( name, wxFileNameFromPath(name) );
415 wxStripExtension( name );
416 wxTheApp->SetAppName( name );
e0253070 417
ec758a20 418 gtk_set_locale();
e0253070 419
ec758a20 420 gtk_init( &argc, &argv );
c801d85f 421
ec758a20 422 GdkColormap *cmap = gdk_colormap_new( gdk_visual_get_system(), TRUE );
0cf2cb36 423
ec758a20
RR
424 for (int i = 0; i < 64; i++)
425 {
426 GdkColor col;
427 col.red = g_palette[i*3 + 0] << 8;
428 col.green = g_palette[i*3 + 1] << 8;
429 col.blue = g_palette[i*3 + 2] << 8;
430 col.pixel = 0;
e0253070 431
ec758a20
RR
432 gdk_color_alloc( cmap, &col );
433 }
e0253070 434
ec758a20 435 gtk_widget_push_colormap( cmap );
e0253070 436
ec758a20 437 gtk_widget_set_default_colormap( cmap );
0cf2cb36 438
ec758a20 439 wxApp::CommonInit();
c801d85f 440
ec758a20
RR
441 wxModule::RegisterModules();
442 if (!wxModule::InitializeModules()) return FALSE;
e0253070 443
ec758a20 444 wxTheApp->OnInitGui();
c801d85f 445
ec758a20
RR
446 // Here frames insert themselves automatically
447 // into wxTopLevelWindows by getting created
448 // in OnInit().
0cf2cb36 449
ec758a20 450 if (!wxTheApp->OnInit()) return 0;
c801d85f 451
ec758a20 452 wxTheApp->m_initialized = (wxTopLevelWindows.Number() > 0);
0cf2cb36 453
ec758a20 454 int retValue = 0;
0cf2cb36 455
ec758a20 456 if (wxTheApp->Initialized()) retValue = wxTheApp->OnRun();
0cf2cb36 457
ec758a20 458 wxTheApp->DeletePendingObjects();
0cf2cb36 459
ec758a20 460 wxTheApp->OnExit();
0cf2cb36 461
ec758a20 462 wxModule::CleanUpModules();
e0253070 463
ec758a20 464 wxApp::CommonCleanUp();
a3622daa 465
ec758a20
RR
466 delete wxTheApp;
467 wxTheApp = (wxApp*) NULL;
0cf2cb36 468
ec758a20 469 wxClassInfo::CleanUpClasses();
e0253070 470
ec758a20 471 delete[] wxBuffer;
e0253070 472
ea57084d 473#if (defined(__WXDEBUG__) && wxUSE_MEMORY_TRACING) || wxUSE_DEBUG_CONTEXT
e0253070 474
ec758a20
RR
475 if (wxDebugContext::CountObjectsLeft() > 0)
476 {
477 wxLogDebug("There were memory leaks.\n");
478 wxDebugContext::Dump();
479 wxDebugContext::PrintStatistics();
480 }
e0253070 481
46dc76ba 482#endif
0cf2cb36 483
ec758a20
RR
484 wxLog *oldLog = wxLog::SetActiveTarget( NULL );
485 if (oldLog) delete oldLog;
184b5d99 486
ec758a20 487 return retValue;
ff7b1510 488}
1a56f55c 489
1a56f55c
RR
490//-----------------------------------------------------------------------------
491