Branch data Line data Source code
1 : : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : : /*************************************************************************
3 : : *
4 : : * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 : : *
6 : : * Copyright 2000, 2010 Oracle and/or its affiliates.
7 : : *
8 : : * OpenOffice.org - a multi-platform office productivity suite
9 : : *
10 : : * This file is part of OpenOffice.org.
11 : : *
12 : : * OpenOffice.org is free software: you can redistribute it and/or modify
13 : : * it under the terms of the GNU Lesser General Public License version 3
14 : : * only, as published by the Free Software Foundation.
15 : : *
16 : : * OpenOffice.org is distributed in the hope that it will be useful,
17 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 : : * GNU Lesser General Public License version 3 for more details
20 : : * (a copy is included in the LICENSE file that accompanied this code).
21 : : *
22 : : * You should have received a copy of the GNU Lesser General Public License
23 : : * version 3 along with OpenOffice.org. If not, see
24 : : * <http://www.openoffice.org/license.html>
25 : : * for a copy of the LGPLv3 License.
26 : : *
27 : : ************************************************************************/
28 : :
29 : :
30 : : #include <stack>
31 : : #include <string.h>
32 : : #include <osl/module.h>
33 : : #define GLIB_DISABLE_DEPRECATION_WARNINGS
34 : : #include <unx/gtk/gtkdata.hxx>
35 : : #include <unx/gtk/gtkinst.hxx>
36 : : #include <unx/salobj.h>
37 : : #include <unx/gtk/gtkframe.hxx>
38 : : #include <unx/gtk/gtkobject.hxx>
39 : : #include <unx/gtk/atkbridge.hxx>
40 : : #include <unx/gtk/gtkprn.hxx>
41 : : #include <headless/svpvd.hxx>
42 : : #include <headless/svpbmp.hxx>
43 : : #include <vcl/apptypes.hxx>
44 : : #include <generic/genpspgraphics.h>
45 : : #include <rtl/strbuf.hxx>
46 : :
47 : : #include <rtl/uri.hxx>
48 : :
49 : : #if OSL_DEBUG_LEVEL > 1
50 : : #include <stdio.h>
51 : : #endif
52 : :
53 : : #include <dlfcn.h>
54 : : #include <fcntl.h>
55 : : #include <unistd.h>
56 : :
57 : : #include "gtkprintwrapper.hxx"
58 : :
59 : 0 : GtkHookedYieldMutex::GtkHookedYieldMutex()
60 : : {
61 : 0 : }
62 : :
63 : : /*
64 : : * These methods always occur in pairs
65 : : * A ThreadsEnter is followed by a ThreadsLeave
66 : : * We need to queue up the recursive lock count
67 : : * for each pair, so we can accurately restore
68 : : * it later.
69 : : */
70 : 0 : void GtkHookedYieldMutex::ThreadsEnter()
71 : : {
72 : 0 : acquire();
73 : 0 : if( !aYieldStack.empty() )
74 : : { /* Previously called ThreadsLeave() */
75 : 0 : sal_uLong nCount = aYieldStack.front();
76 : 0 : aYieldStack.pop_front();
77 : 0 : while( nCount-- > 1 )
78 : 0 : acquire();
79 : : }
80 : 0 : }
81 : :
82 : 0 : void GtkHookedYieldMutex::ThreadsLeave()
83 : : {
84 : 0 : aYieldStack.push_front( mnCount );
85 : :
86 : : #if OSL_DEBUG_LEVEL > 1
87 : : if( mnThreadId &&
88 : : mnThreadId != osl::Thread::getCurrentIdentifier())
89 : : fprintf( stderr, "\n\n--- A different thread owns the mutex ...---\n\n\n");
90 : : #endif
91 : :
92 : 0 : while( mnCount > 1 )
93 : 0 : release();
94 : 0 : release();
95 : 0 : }
96 : :
97 : 0 : void GtkHookedYieldMutex::acquire()
98 : : {
99 : 0 : SalYieldMutex::acquire();
100 : 0 : }
101 : :
102 : 0 : void GtkHookedYieldMutex::release()
103 : : {
104 : 0 : SalYieldMutex::release();
105 : 0 : }
106 : :
107 : : extern "C"
108 : : {
109 : : #define GET_YIELD_MUTEX() static_cast<GtkHookedYieldMutex*>(GetSalData()->m_pInstance->GetYieldMutex())
110 : 0 : static void GdkThreadsEnter( void )
111 : : {
112 : 0 : GtkHookedYieldMutex *pYieldMutex = GET_YIELD_MUTEX();
113 : 0 : pYieldMutex->ThreadsEnter();
114 : 0 : }
115 : 0 : static void GdkThreadsLeave( void )
116 : : {
117 : 0 : GtkHookedYieldMutex *pYieldMutex = GET_YIELD_MUTEX();
118 : 0 : pYieldMutex->ThreadsLeave();
119 : 0 : }
120 : 0 : static bool hookLocks( oslModule pModule )
121 : : {
122 : : typedef void (*GdkLockFn) (GCallback enter_fn, GCallback leave_fn);
123 : :
124 : : GdkLockFn gdk_threads_set_lock_functions =
125 : 0 : (GdkLockFn) osl_getAsciiFunctionSymbol( pModule, "gdk_threads_set_lock_functions" );
126 : 0 : if ( !gdk_threads_set_lock_functions )
127 : : {
128 : : #if OSL_DEBUG_LEVEL > 1
129 : : fprintf( stderr, "Failed to hook gdk threads locks\n" );
130 : : #endif
131 : 0 : return false;
132 : : }
133 : :
134 : 0 : gdk_threads_set_lock_functions (GdkThreadsEnter, GdkThreadsLeave);
135 : : #if OSL_DEBUG_LEVEL > 1
136 : : fprintf( stderr, "Hooked gdk threads locks\n" );
137 : : #endif
138 : 0 : return true;
139 : : }
140 : :
141 : 0 : VCLPLUG_GTK_PUBLIC SalInstance* create_SalInstance( oslModule pModule )
142 : : {
143 : : #if OSL_DEBUG_LEVEL > 0
144 : : fprintf( stderr, "create vcl plugin instance with gtk version %d %d %d\n",
145 : : (int) gtk_major_version, (int) gtk_minor_version,
146 : : (int) gtk_micro_version );
147 : : #endif
148 : : /* #i92121# workaround deadlocks in the X11 implementation
149 : : */
150 : 0 : static const char* pNoXInitThreads = getenv( "SAL_NO_XINITTHREADS" );
151 : : /* #i90094#
152 : : from now on we know that an X connection will be
153 : : established, so protect X against itself
154 : : */
155 : 0 : if( ! ( pNoXInitThreads && *pNoXInitThreads ) )
156 : 0 : XInitThreads();
157 : :
158 : : #if GTK_CHECK_VERSION(3,0,0)
159 : : const gchar* pVersion = gtk_check_version( 3, 2, 0 );
160 : : #else
161 : 0 : const gchar* pVersion = gtk_check_version( 2, 2, 0 );
162 : : #endif
163 : 0 : if( pVersion )
164 : : {
165 : : #if OSL_DEBUG_LEVEL > 1
166 : : fprintf( stderr, "gtk version conflict: %s\n", pVersion );
167 : : #endif
168 : 0 : return NULL;
169 : : }
170 : :
171 : : GtkYieldMutex *pYieldMutex;
172 : :
173 : : // init gdk thread protection
174 : : if ( !g_thread_supported() )
175 : : g_thread_init( NULL );
176 : :
177 : 0 : if ( hookLocks( pModule ) )
178 : 0 : pYieldMutex = new GtkHookedYieldMutex();
179 : : else
180 : : #if GTK_CHECK_VERSION(3,0,0)
181 : : g_error ("impossible case for gtk3");
182 : : #else
183 : 0 : pYieldMutex = new GtkYieldMutex();
184 : : #endif
185 : :
186 : 0 : gdk_threads_init();
187 : :
188 : 0 : GtkInstance* pInstance = new GtkInstance( pYieldMutex );
189 : : #if OSL_DEBUG_LEVEL > 1
190 : : fprintf( stderr, "creating GtkSalInstance 0x%p\n", pInstance );
191 : : #endif
192 : :
193 : : // initialize SalData
194 : 0 : GtkData *pSalData = new GtkData( pInstance );
195 : 0 : pSalData->Init();
196 : 0 : pSalData->initNWF();
197 : :
198 : 0 : pInstance->Init();
199 : :
200 : 0 : InitAtkBridge();
201 : :
202 : 0 : return pInstance;
203 : : }
204 : : }
205 : :
206 : : #if GTK_CHECK_VERSION(3,0,0)
207 : : static sal_uInt16 categorizeEvent(const GdkEvent *pEvent)
208 : : {
209 : : sal_uInt16 nType = 0;
210 : : switch( pEvent->type )
211 : : {
212 : : case GDK_MOTION_NOTIFY:
213 : : case GDK_BUTTON_PRESS:
214 : : case GDK_2BUTTON_PRESS:
215 : : case GDK_3BUTTON_PRESS:
216 : : case GDK_BUTTON_RELEASE:
217 : : case GDK_ENTER_NOTIFY:
218 : : case GDK_LEAVE_NOTIFY:
219 : : case GDK_SCROLL:
220 : : nType = VCL_INPUT_MOUSE;
221 : : break;
222 : : case GDK_KEY_PRESS:
223 : : case GDK_KEY_RELEASE:
224 : : nType = VCL_INPUT_KEYBOARD;
225 : : break;
226 : : case GDK_EXPOSE:
227 : : nType = VCL_INPUT_PAINT;
228 : : break;
229 : : default:
230 : : nType = VCL_INPUT_OTHER;
231 : : break;
232 : : }
233 : : return nType;
234 : : }
235 : : #endif
236 : :
237 : 0 : GtkInstance::GtkInstance( SalYieldMutex* pMutex )
238 : : #if GTK_CHECK_VERSION(3,0,0)
239 : : : SvpSalInstance( pMutex )
240 : : #else
241 : 0 : : X11SalInstance( pMutex )
242 : : #endif
243 : : {
244 : 0 : }
245 : :
246 : : // This has to happen after gtk_init has been called by saldata.cxx's
247 : : // Init or our handlers just get clobbered.
248 : 0 : void GtkInstance::Init()
249 : : {
250 : 0 : }
251 : :
252 : 0 : GtkInstance::~GtkInstance()
253 : : {
254 : 0 : while( !m_aTimers.empty() )
255 : 0 : delete *m_aTimers.begin();
256 : 0 : DeInitAtkBridge();
257 : 0 : }
258 : :
259 : 0 : SalFrame* GtkInstance::CreateFrame( SalFrame* pParent, sal_uLong nStyle )
260 : : {
261 : 0 : return new GtkSalFrame( pParent, nStyle );
262 : : }
263 : :
264 : 0 : SalFrame* GtkInstance::CreateChildFrame( SystemParentData* pParentData, sal_uLong )
265 : : {
266 : 0 : return new GtkSalFrame( pParentData );
267 : : }
268 : :
269 : 0 : SalObject* GtkInstance::CreateObject( SalFrame* pParent, SystemWindowData* pWindowData, sal_Bool bShow )
270 : : {
271 : : #if !GTK_CHECK_VERSION(3,0,0)
272 : : // there is no method to set a visual for a GtkWidget
273 : : // so we need the X11SalObject in that case
274 : 0 : if( pWindowData )
275 : 0 : return X11SalObject::CreateObject( pParent, pWindowData, bShow );
276 : : #else
277 : : (void)pWindowData;
278 : : #warning FIXME: Missing CreateObject functionality ...
279 : : #endif
280 : :
281 : 0 : return new GtkSalObject( static_cast<GtkSalFrame*>(pParent), bShow );
282 : : }
283 : :
284 : : extern "C"
285 : : {
286 : : typedef void*(* getDefaultFnc)();
287 : : typedef void(* addItemFnc)(void *, const char *);
288 : : }
289 : :
290 : 0 : void GtkInstance::AddToRecentDocumentList(const rtl::OUString& rFileUrl, const rtl::OUString& rMimeType)
291 : : {
292 : 0 : rtl::OString sGtkURL;
293 : 0 : rtl_TextEncoding aSystemEnc = osl_getThreadTextEncoding();
294 : 0 : if ((aSystemEnc == RTL_TEXTENCODING_UTF8) || (rFileUrl.compareToAscii( "file://", 7 ) != 0))
295 : 0 : sGtkURL = rtl::OUStringToOString(rFileUrl, RTL_TEXTENCODING_UTF8);
296 : : else
297 : : {
298 : : //Non-utf8 locales are a bad idea if trying to work with non-ascii filenames
299 : : //Decode %XX components
300 : 0 : rtl::OUString sDecodedUri = rtl::Uri::decode(rFileUrl.copy(7), rtl_UriDecodeToIuri, RTL_TEXTENCODING_UTF8);
301 : : //Convert back to system locale encoding
302 : 0 : rtl::OString sSystemUrl = rtl::OUStringToOString(sDecodedUri, aSystemEnc);
303 : : //Encode to an escaped ASCII-encoded URI
304 : 0 : gchar *g_uri = g_filename_to_uri(sSystemUrl.getStr(), NULL, NULL);
305 : 0 : sGtkURL = rtl::OString(g_uri);
306 : 0 : g_free(g_uri);
307 : : }
308 : : #if GTK_CHECK_VERSION(2,10,0)
309 : 0 : GtkRecentManager *manager = gtk_recent_manager_get_default ();
310 : 0 : gtk_recent_manager_add_item (manager, sGtkURL.getStr());
311 : 0 : (void)rMimeType;
312 : : #else
313 : : static getDefaultFnc sym_gtk_recent_manager_get_default =
314 : : (getDefaultFnc)osl_getAsciiFunctionSymbol( GetSalData()->m_pPlugin, "gtk_recent_manager_get_default" );
315 : :
316 : : static addItemFnc sym_gtk_recent_manager_add_item =
317 : : (addItemFnc)osl_getAsciiFunctionSymbol( GetSalData()->m_pPlugin, "gtk_recent_manager_add_item");
318 : : if (sym_gtk_recent_manager_get_default && sym_gtk_recent_manager_add_item)
319 : : sym_gtk_recent_manager_add_item(sym_gtk_recent_manager_get_default(), sGtkURL.getStr());
320 : : else
321 : : X11SalInstance::AddToRecentDocumentList(rFileUrl, rMimeType);
322 : : #endif
323 : 0 : }
324 : :
325 : : /*
326 : : * Obsolete, non-working, and crufty code from the
327 : : * beginning of time. When we update our base platform
328 : : * we should kill this with extreme prejudice.
329 : : */
330 : : #if !GTK_CHECK_VERSION(3,0,0)
331 : : # define HORRIBLE_OBSOLETE_YIELDMUTEX_IMPL
332 : : #endif
333 : :
334 : 0 : SalInfoPrinter* GtkInstance::CreateInfoPrinter( SalPrinterQueueInfo* pQueueInfo,
335 : : ImplJobSetup* pSetupData )
336 : : {
337 : : #if defined ENABLE_GTK_PRINT || GTK_CHECK_VERSION(3,0,0)
338 : 0 : mbPrinterInit = true;
339 : : // create and initialize SalInfoPrinter
340 : 0 : PspSalInfoPrinter* pPrinter = new GtkSalInfoPrinter;
341 : 0 : configurePspInfoPrinter(pPrinter, pQueueInfo, pSetupData);
342 : 0 : return pPrinter;
343 : : #else
344 : : return Superclass_t::CreateInfoPrinter( pQueueInfo, pSetupData );
345 : : #endif
346 : : }
347 : :
348 : 0 : SalPrinter* GtkInstance::CreatePrinter( SalInfoPrinter* pInfoPrinter )
349 : : {
350 : : #if defined ENABLE_GTK_PRINT || GTK_CHECK_VERSION(3,0,0)
351 : 0 : mbPrinterInit = true;
352 : 0 : fprintf(stderr, "gtk printer\n");
353 : 0 : return new GtkSalPrinter( pInfoPrinter );
354 : : #else
355 : : return Superclass_t::CreatePrinter( pInfoPrinter );
356 : : #endif
357 : : }
358 : :
359 : :
360 : 0 : GtkYieldMutex::GtkYieldMutex()
361 : : {
362 : 0 : }
363 : :
364 : 0 : void GtkYieldMutex::acquire()
365 : : {
366 : : #ifdef HORRIBLE_OBSOLETE_YIELDMUTEX_IMPL
367 : 0 : oslThreadIdentifier aCurrentThread = osl::Thread::getCurrentIdentifier();
368 : : // protect member manipulation
369 : 0 : SolarMutexObject::acquire();
370 : 0 : if( mnCount > 0 && mnThreadId == aCurrentThread )
371 : : {
372 : 0 : mnCount++;
373 : 0 : SolarMutexObject::release();
374 : 0 : return;
375 : : }
376 : 0 : SolarMutexObject::release();
377 : :
378 : : // obtain gdk mutex
379 : 0 : gdk_threads_enter();
380 : :
381 : : // obtained gdk mutex, now lock count is one by definition
382 : 0 : SolarMutexObject::acquire();
383 : 0 : mnCount = 1;
384 : 0 : mnThreadId = aCurrentThread;
385 : 0 : SolarMutexObject::release();
386 : : #else
387 : : g_error ("never called");
388 : : #endif
389 : : }
390 : :
391 : 0 : void GtkYieldMutex::release()
392 : : {
393 : : #ifdef HORRIBLE_OBSOLETE_YIELDMUTEX_IMPL
394 : 0 : oslThreadIdentifier aCurrentThread = osl::Thread::getCurrentIdentifier();
395 : : // protect member manipulation
396 : 0 : SolarMutexObject::acquire();
397 : : // strange things happen, do nothing if we don't own the mutex
398 : 0 : if( mnThreadId == aCurrentThread )
399 : : {
400 : 0 : mnCount--;
401 : 0 : if( mnCount == 0 )
402 : : {
403 : 0 : gdk_threads_leave();
404 : 0 : mnThreadId = 0;
405 : : }
406 : : }
407 : 0 : SolarMutexObject::release();
408 : : #else
409 : : g_error ("never called");
410 : : #endif
411 : 0 : }
412 : :
413 : 0 : sal_Bool GtkYieldMutex::tryToAcquire()
414 : : {
415 : : #ifdef HORRIBLE_OBSOLETE_YIELDMUTEX_IMPL
416 : 0 : oslThreadIdentifier aCurrentThread = osl::Thread::getCurrentIdentifier();
417 : : // protect member manipulation
418 : 0 : SolarMutexObject::acquire();
419 : 0 : if( mnCount > 0 )
420 : : {
421 : 0 : if( mnThreadId == aCurrentThread )
422 : : {
423 : 0 : mnCount++;
424 : 0 : SolarMutexObject::release();
425 : 0 : return sal_True;
426 : : }
427 : : else
428 : : {
429 : 0 : SolarMutexObject::release();
430 : 0 : return sal_False;
431 : : }
432 : : }
433 : 0 : SolarMutexObject::release();
434 : :
435 : : // HACK: gdk_threads_mutex is private, we shouldn't use it.
436 : : // how to we do a try_lock without having a gdk_threads_try_enter ?
437 : 0 : if( ! g_mutex_trylock( gdk_threads_mutex ) )
438 : 0 : return sal_False;
439 : :
440 : : // obtained gdk mutex, now lock count is one by definition
441 : 0 : SolarMutexObject::acquire();
442 : 0 : mnCount = 1;
443 : 0 : mnThreadId = aCurrentThread;
444 : 0 : SolarMutexObject::release();
445 : :
446 : : #else
447 : : g_error ("never called");
448 : : #endif
449 : 0 : return sal_True;
450 : : }
451 : :
452 : 0 : int GtkYieldMutex::Grab()
453 : : {
454 : : #ifdef HORRIBLE_OBSOLETE_YIELDMUTEX_IMPL
455 : : // this MUST only be called by gdk/gtk callbacks:
456 : : // they are entered with gdk mutex locked; the mutex
457 : : // was unlocked by GtkYieldMutex befor yielding which
458 : : // is now locked again by gtk implicitly
459 : :
460 : : // obtained gdk mutex, now lock count is one by definition
461 : 0 : SolarMutexObject::acquire();
462 : 0 : int nRet = mnCount;
463 : 0 : if( mnCount == 0 ) // recursive else
464 : 0 : mnThreadId = osl::Thread::getCurrentIdentifier();
465 : : #if OSL_DEBUG_LEVEL > 1
466 : : else if( mnThreadId != osl::Thread::getCurrentIdentifier() )
467 : : {
468 : : fprintf( stderr, "Yield mutex grabbed in different thread !\n" );
469 : : abort();
470 : : }
471 : : #endif
472 : 0 : mnCount = 1;
473 : 0 : SolarMutexObject::release();
474 : 0 : return nRet;
475 : : #else
476 : : g_error ("never called");
477 : : return sal_True;
478 : : #endif
479 : : }
480 : :
481 : 0 : void GtkYieldMutex::Ungrab( int nGrabs )
482 : : {
483 : : #ifdef HORRIBLE_OBSOLETE_YIELDMUTEX_IMPL
484 : : // this MUST only be called when leaving the callback
485 : : // that locked the mutex with Grab()
486 : 0 : SolarMutexObject::acquire();
487 : 0 : mnCount = nGrabs;
488 : 0 : if( mnCount == 0 )
489 : 0 : mnThreadId = 0;
490 : 0 : SolarMutexObject::release();
491 : : #else
492 : : (void)nGrabs;
493 : : g_error ("never called");
494 : : #endif
495 : 0 : }
496 : :
497 : 0 : SalVirtualDevice* GtkInstance::CreateVirtualDevice( SalGraphics *pG,
498 : : long nDX, long nDY,
499 : : sal_uInt16 nBitCount,
500 : : const SystemGraphicsData *pGd )
501 : : {
502 : : #if GTK_CHECK_VERSION(3,0,0)
503 : : (void)pG; (void) pGd;
504 : : SvpSalVirtualDevice* pNew = new SvpSalVirtualDevice( nBitCount );
505 : : pNew->SetSize( nDX, nDY );
506 : : return pNew;
507 : : #else
508 : 0 : return X11SalInstance::CreateVirtualDevice( pG, nDX, nDY, nBitCount, pGd );
509 : : #endif
510 : : }
511 : :
512 : 0 : SalBitmap* GtkInstance::CreateSalBitmap()
513 : : {
514 : : #if GTK_CHECK_VERSION(3,0,0)
515 : : return new SvpSalBitmap();
516 : : #else
517 : 0 : return X11SalInstance::CreateSalBitmap();
518 : : #endif
519 : : }
520 : :
521 : 0 : SalTimer* GtkInstance::CreateSalTimer()
522 : : {
523 : 0 : GtkSalTimer *pTimer = new GtkSalTimer();
524 : 0 : m_aTimers.push_back( pTimer );
525 : 0 : return pTimer;
526 : : }
527 : :
528 : 0 : void GtkInstance::RemoveTimer (SalTimer *pTimer)
529 : : {
530 : 0 : std::vector<GtkSalTimer *>::iterator it;
531 : 0 : it = std::find( m_aTimers.begin(), m_aTimers.end(), pTimer );
532 : 0 : if( it != m_aTimers.end() )
533 : 0 : m_aTimers.erase( it );
534 : 0 : }
535 : :
536 : 0 : void GtkInstance::Yield( bool bWait, bool bHandleAllCurrentEvents )
537 : : {
538 : 0 : GetGtkSalData()->Yield( bWait, bHandleAllCurrentEvents );
539 : 0 : }
540 : :
541 : 0 : bool GtkInstance::IsTimerExpired()
542 : : {
543 : 0 : for( std::vector<GtkSalTimer *>::iterator it = m_aTimers.begin();
544 : 0 : it != m_aTimers.end(); ++it )
545 : 0 : if( (*it)->Expired() )
546 : 0 : return true;
547 : :
548 : 0 : return false;
549 : : }
550 : :
551 : 0 : bool GtkInstance::AnyInput( sal_uInt16 nType )
552 : : {
553 : 0 : if( (nType & VCL_INPUT_TIMER) && IsTimerExpired() )
554 : 0 : return true;
555 : : #if !GTK_CHECK_VERSION(3,0,0)
556 : 0 : bool bRet = X11SalInstance::AnyInput(nType);
557 : : #else
558 : : if (!gdk_events_pending())
559 : : return false;
560 : :
561 : : if (nType == VCL_INPUT_ANY)
562 : : return true;
563 : :
564 : : bool bRet = false;
565 : : std::stack<GdkEvent*> aEvents;
566 : : GdkEvent *pEvent = NULL;
567 : : while ((pEvent = gdk_event_get()))
568 : : {
569 : : aEvents.push(pEvent);
570 : : sal_uInt16 nEventType = categorizeEvent(pEvent);
571 : : if ( (nEventType & nType) || ( ! nEventType && (nType & VCL_INPUT_OTHER) ) )
572 : : {
573 : : bRet = true;
574 : : break;
575 : : }
576 : : }
577 : :
578 : : while (!aEvents.empty())
579 : : {
580 : : pEvent = aEvents.top();
581 : : gdk_event_put(pEvent);
582 : : gdk_event_free(pEvent);
583 : : aEvents.pop();
584 : : }
585 : : #endif
586 : 0 : return bRet;
587 : : }
588 : :
589 : 0 : GenPspGraphics *GtkInstance::CreatePrintGraphics()
590 : : {
591 : 0 : return new GenPspGraphics();
592 : : }
593 : :
594 : : boost::shared_ptr<vcl::unx::GtkPrintWrapper>
595 : 0 : GtkInstance::getPrintWrapper() const
596 : : {
597 : 0 : if (!m_pPrintWrapper)
598 : 0 : m_pPrintWrapper.reset(new vcl::unx::GtkPrintWrapper);
599 : 0 : return m_pPrintWrapper;
600 : : }
601 : :
602 : : #if GTK_CHECK_VERSION(3,0,0)
603 : : #include "../../../headless/svpinst.cxx"
604 : : #endif
605 : :
606 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|