1/****************************************************************************
2**
3** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies).
4** Contact: http://www.qt-project.org/legal
5**
6** This file is part of the QtGui module of the Qt Toolkit.
7**
8** $QT_BEGIN_LICENSE:LGPL$
9** Commercial License Usage
10** Licensees holding valid commercial Qt licenses may use this file in
11** accordance with the commercial license agreement provided with the
12** Software or, alternatively, in accordance with the terms contained in
13** a written agreement between you and Digia. For licensing terms and
14** conditions see http://qt.digia.com/licensing. For further information
15** use the contact form at http://qt.digia.com/contact-us.
16**
17** GNU Lesser General Public License Usage
18** Alternatively, this file may be used under the terms of the GNU Lesser
19** General Public License version 2.1 as published by the Free Software
20** Foundation and appearing in the file LICENSE.LGPL included in the
21** packaging of this file. Please review the following information to
22** ensure the GNU Lesser General Public License version 2.1 requirements
23** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
24**
25** In addition, as a special exception, Digia gives you certain additional
26** rights. These rights are described in the Digia Qt LGPL Exception
27** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
28**
29** GNU General Public License Usage
30** Alternatively, this file may be used under the terms of the GNU
31** General Public License version 3.0 as published by the Free Software
32** Foundation and appearing in the file LICENSE.GPL included in the
33** packaging of this file. Please review the following information to
34** ensure the GNU General Public License version 3.0 requirements will be
35** met: http://www.gnu.org/copyleft/gpl.html.
36**
37**
38** $QT_END_LICENSE$
39**
40****************************************************************************/
41
42#include "qplatformdefs.h"
43#include "qabstracteventdispatcher.h"
44#include "qaccessible.h"
45#include "qapplication.h"
46#include "qclipboard.h"
47#include "qcursor.h"
48#include "qdesktopwidget.h"
49#include "qdir.h"
50#include "qevent.h"
51#include "qfile.h"
52#include "qfileinfo.h"
53#include "qgraphicsscene.h"
54#include "qhash.h"
55#include "qset.h"
56#include "qlayout.h"
57#include "qsessionmanager.h"
58#include "qstyle.h"
59#include "qstylefactory.h"
60#include "qtextcodec.h"
61#include "qtranslator.h"
62#include "qvariant.h"
63#include "qwidget.h"
64#include "qdnd_p.h"
65#include "qcolormap.h"
66#include "qdebug.h"
67#include "private/qgraphicssystemfactory_p.h"
68#include "private/qgraphicssystem_p.h"
69#include "private/qstylesheetstyle_p.h"
70#include "private/qstyle_p.h"
71#include "qmessagebox.h"
72#include <QtGui/qgraphicsproxywidget.h>
73
74#ifdef QT_GRAPHICSSYSTEM_RUNTIME
75#include "private/qgraphicssystem_runtime_p.h"
76#endif
77
78#include "qinputcontext.h"
79#include "qkeymapper_p.h"
80
81#ifdef Q_WS_X11
82#include <private/qt_x11_p.h>
83#endif
84
85#if defined(Q_WS_X11) || defined(Q_OS_SYMBIAN)
86#include "qinputcontextfactory.h"
87#endif
88
89#include "qguiplatformplugin_p.h"
90
91#include <qthread.h>
92#include <private/qthread_p.h>
93
94#include <private/qfont_p.h>
95
96#include <stdlib.h>
97
98#if defined(Q_WS_X11) && !defined(QT_NO_EGL)
99#include <link.h>
100#endif
101
102#include "qapplication_p.h"
103#include "qevent_p.h"
104#include "qwidget_p.h"
105
106#include "qapplication.h"
107
108#include "qgesture.h"
109#include "private/qgesturemanager_p.h"
110
111#ifndef QT_NO_LIBRARY
112#include "qlibrary.h"
113#endif
114
115#ifdef Q_WS_WINCE
116#include "qdatetime.h"
117#include "qguifunctions_wince.h"
118extern bool qt_wince_is_smartphone(); //qguifunctions_wince.cpp
119extern bool qt_wince_is_mobile(); //qguifunctions_wince.cpp
120extern bool qt_wince_is_pocket_pc(); //qguifunctions_wince.cpp
121#endif
122
123#include "qdatetime.h"
124
125#ifdef QT_MAC_USE_COCOA
126#include <private/qt_cocoa_helpers_mac_p.h>
127#endif
128
129//#define ALIEN_DEBUG
130
131#if defined(Q_OS_SYMBIAN)
132#include "qt_s60_p.h"
133#endif
134
135static void initResources()
136{
137#if defined(Q_WS_WINCE)
138 Q_INIT_RESOURCE_EXTERN(qstyle_wince)
139 Q_INIT_RESOURCE(qstyle_wince);
140#elif defined(Q_OS_SYMBIAN)
141 Q_INIT_RESOURCE_EXTERN(qstyle_s60)
142 Q_INIT_RESOURCE(qstyle_s60);
143#else
144 Q_INIT_RESOURCE_EXTERN(qstyle)
145 Q_INIT_RESOURCE(qstyle);
146#endif
147 Q_INIT_RESOURCE_EXTERN(qmessagebox)
148 Q_INIT_RESOURCE(qmessagebox);
149#if !defined(QT_NO_PRINTDIALOG)
150 Q_INIT_RESOURCE_EXTERN(qprintdialog)
151 Q_INIT_RESOURCE(qprintdialog);
152#endif
153#ifdef Q_WS_MAC
154 Q_INIT_RESOURCE_EXTERN(macresources)
155 Q_INIT_RESOURCE(macresources);
156#endif
157}
158
159QT_BEGIN_NAMESPACE
160
161Q_CORE_EXPORT void qt_call_post_routines();
162
163QApplication::Type qt_appType=QApplication::Tty;
164QApplicationPrivate *QApplicationPrivate::self = 0;
165
166QInputContext *QApplicationPrivate::inputContext = 0;
167
168bool QApplicationPrivate::quitOnLastWindowClosed = true;
169
170#ifdef Q_OS_SYMBIAN
171bool QApplicationPrivate::inputContextBeingCreated = false;
172#endif
173
174#ifdef Q_WS_WINCE
175int QApplicationPrivate::autoMaximizeThreshold = -1;
176bool QApplicationPrivate::autoSipEnabled = false;
177#else
178bool QApplicationPrivate::autoSipEnabled = true;
179#endif
180
181QApplicationPrivate::QApplicationPrivate(int &argc, char **argv, QApplication::Type type, int flags)
182 : QCoreApplicationPrivate(argc, argv, flags)
183{
184 application_type = type;
185 qt_appType = type;
186
187#ifndef QT_NO_SESSIONMANAGER
188 is_session_restored = false;
189#endif
190
191 quitOnLastWindowClosed = true;
192
193#ifdef QT3_SUPPORT
194 qt_compat_used = 0;
195 qt_compat_resolved = 0;
196 qt_tryAccelEvent = 0;
197 qt_tryComposeUnicode = 0;
198 qt_dispatchAccelEvent = 0;
199#endif
200#if defined(Q_WS_QWS) && !defined(QT_NO_DIRECTPAINTER)
201 directPainters = 0;
202#endif
203
204#ifndef QT_NO_GESTURES
205 gestureManager = 0;
206 gestureWidget = 0;
207#endif // QT_NO_GESTURES
208
209#if defined(Q_WS_X11) || defined(Q_WS_WIN)
210 move_cursor = 0;
211 copy_cursor = 0;
212 link_cursor = 0;
213#endif
214#if defined(Q_WS_WIN)
215 ignore_cursor = 0;
216#endif
217
218 if (!self)
219 self = this;
220}
221
222QApplicationPrivate::~QApplicationPrivate()
223{
224 if (self == this)
225 self = 0;
226}
227
228/*!
229 \class QApplication
230 \brief The QApplication class manages the GUI application's control
231 flow and main settings.
232
233 QApplication contains the main event loop, where all events from the window
234 system and other sources are processed and dispatched. It also handles the
235 application's initialization, finalization, and provides session
236 management. In addition, QApplication handles most of the system-wide and
237 application-wide settings.
238
239 For any GUI application using Qt, there is precisely \bold one QApplication
240 object, no matter whether the application has 0, 1, 2 or more windows at
241 any given time. For non-GUI Qt applications, use QCoreApplication instead,
242 as it does not depend on the \l QtGui library.
243
244 The QApplication object is accessible through the instance() function that
245 returns a pointer equivalent to the global qApp pointer.
246
247 QApplication's main areas of responsibility are:
248 \list
249 \o It initializes the application with the user's desktop settings
250 such as palette(), font() and doubleClickInterval(). It keeps
251 track of these properties in case the user changes the desktop
252 globally, for example through some kind of control panel.
253
254 \o It performs event handling, meaning that it receives events
255 from the underlying window system and dispatches them to the
256 relevant widgets. By using sendEvent() and postEvent() you can
257 send your own events to widgets.
258
259 \o It parses common command line arguments and sets its internal
260 state accordingly. See the \l{QApplication::QApplication()}
261 {constructor documentation} below for more details.
262
263 \o It defines the application's look and feel, which is
264 encapsulated in a QStyle object. This can be changed at runtime
265 with setStyle().
266
267 \o It specifies how the application is to allocate colors. See
268 setColorSpec() for details.
269
270 \o It provides localization of strings that are visible to the
271 user via translate().
272
273 \o It provides some magical objects like the desktop() and the
274 clipboard().
275
276 \o It knows about the application's windows. You can ask which
277 widget is at a certain position using widgetAt(), get a list of
278 topLevelWidgets() and closeAllWindows(), etc.
279
280 \o It manages the application's mouse cursor handling, see
281 setOverrideCursor()
282
283 \o On the X window system, it provides functions to flush and sync
284 the communication stream, see flushX() and syncX().
285
286 \o It provides support for sophisticated \l{Session Management}
287 {session management}. This makes it possible for applications
288 to terminate gracefully when the user logs out, to cancel a
289 shutdown process if termination isn't possible and even to
290 preserve the entire application's state for a future session.
291 See isSessionRestored(), sessionId() and commitData() and
292 saveState() for details.
293 \endlist
294
295 Since the QApplication object does so much initialization, it \e{must} be
296 created before any other objects related to the user interface are created.
297 QApplication also deals with common command line arguments. Hence, it is
298 usually a good idea to create it \e before any interpretation or
299 modification of \c argv is done in the application itself.
300
301 \table
302 \header
303 \o{2,1} Groups of functions
304
305 \row
306 \o System settings
307 \o desktopSettingsAware(),
308 setDesktopSettingsAware(),
309 cursorFlashTime(),
310 setCursorFlashTime(),
311 doubleClickInterval(),
312 setDoubleClickInterval(),
313 setKeyboardInputInterval(),
314 wheelScrollLines(),
315 setWheelScrollLines(),
316 palette(),
317 setPalette(),
318 font(),
319 setFont(),
320 fontMetrics().
321
322 \row
323 \o Event handling
324 \o exec(),
325 processEvents(),
326 exit(),
327 quit().
328 sendEvent(),
329 postEvent(),
330 sendPostedEvents(),
331 removePostedEvents(),
332 hasPendingEvents(),
333 notify(),
334 macEventFilter(),
335 qwsEventFilter(),
336 x11EventFilter(),
337 x11ProcessEvent(),
338 winEventFilter().
339
340 \row
341 \o GUI Styles
342 \o style(),
343 setStyle().
344
345 \row
346 \o Color usage
347 \o colorSpec(),
348 setColorSpec(),
349 qwsSetCustomColors().
350
351 \row
352 \o Text handling
353 \o installTranslator(),
354 removeTranslator()
355 translate().
356
357 \row
358 \o Widgets
359 \o allWidgets(),
360 topLevelWidgets(),
361 desktop(),
362 activePopupWidget(),
363 activeModalWidget(),
364 clipboard(),
365 focusWidget(),
366 activeWindow(),
367 widgetAt().
368
369 \row
370 \o Advanced cursor handling
371 \o overrideCursor(),
372 setOverrideCursor(),
373 restoreOverrideCursor().
374
375 \row
376 \o X Window System synchronization
377 \o flushX(),
378 syncX().
379
380 \row
381 \o Session management
382 \o isSessionRestored(),
383 sessionId(),
384 commitData(),
385 saveState().
386
387 \row
388 \o Miscellaneous
389 \o closeAllWindows(),
390 startingUp(),
391 closingDown(),
392 type().
393 \endtable
394
395 \sa QCoreApplication, QAbstractEventDispatcher, QEventLoop, QSettings
396*/
397
398/*!
399 \enum QApplication::Type
400
401 \value Tty a console application
402 \value GuiClient a GUI client application
403 \value GuiServer a GUI server application (for Qt for Embedded Linux)
404*/
405
406/*!
407 \enum QApplication::ColorSpec
408
409 \value NormalColor the default color allocation policy
410 \value CustomColor the same as NormalColor for X11; allocates colors
411 to a palette on demand under Windows
412 \value ManyColor the right choice for applications that use thousands of
413 colors
414
415 See setColorSpec() for full details.
416*/
417
418/*!
419 \fn QWidget *QApplication::topLevelAt(const QPoint &point)
420
421 Returns the top-level widget at the given \a point; returns 0 if
422 there is no such widget.
423*/
424
425/*!
426 \fn QWidget *QApplication::topLevelAt(int x, int y)
427
428 \overload
429
430 Returns the top-level widget at the point (\a{x}, \a{y}); returns
431 0 if there is no such widget.
432*/
433
434
435/*
436 The qt_init() and qt_cleanup() functions are implemented in the
437 qapplication_xyz.cpp file.
438*/
439
440void qt_init(QApplicationPrivate *priv, int type
441#ifdef Q_WS_X11
442 , Display *display = 0, Qt::HANDLE visual = 0, Qt::HANDLE colormap = 0
443#endif
444 );
445void qt_cleanup();
446
447Qt::MouseButtons QApplicationPrivate::mouse_buttons = Qt::NoButton;
448Qt::KeyboardModifiers QApplicationPrivate::modifier_buttons = Qt::NoModifier;
449
450QStyle *QApplicationPrivate::app_style = 0; // default application style
451QString QApplicationPrivate::styleOverride; // style override
452
453#ifndef QT_NO_STYLE_STYLESHEET
454QString QApplicationPrivate::styleSheet; // default application stylesheet
455#endif
456QPointer<QWidget> QApplicationPrivate::leaveAfterRelease = 0;
457
458int QApplicationPrivate::app_cspec = QApplication::NormalColor;
459QPalette *QApplicationPrivate::app_pal = 0; // default application palette
460QPalette *QApplicationPrivate::sys_pal = 0; // default system palette
461QPalette *QApplicationPrivate::set_pal = 0; // default palette set by programmer
462
463QGraphicsSystem *QApplicationPrivate::graphics_system = 0; // default graphics system
464#if defined(Q_WS_QPA)
465QPlatformIntegration *QApplicationPrivate::platform_integration = 0;
466#endif
467QString QApplicationPrivate::graphics_system_name; // graphics system id - for delayed initialization
468bool QApplicationPrivate::runtime_graphics_system = false;
469
470Q_GLOBAL_STATIC(QMutex, applicationFontMutex)
471QFont *QApplicationPrivate::app_font = 0; // default application font
472QFont *QApplicationPrivate::sys_font = 0; // default system font
473QFont *QApplicationPrivate::set_font = 0; // default font set by programmer
474
475QIcon *QApplicationPrivate::app_icon = 0;
476QWidget *QApplicationPrivate::main_widget = 0; // main application widget
477QWidget *QApplicationPrivate::focus_widget = 0; // has keyboard input focus
478QWidget *QApplicationPrivate::hidden_focus_widget = 0; // will get keyboard input focus after show()
479QWidget *QApplicationPrivate::active_window = 0; // toplevel with keyboard focus
480bool QApplicationPrivate::obey_desktop_settings = true; // use winsys resources
481int QApplicationPrivate::cursor_flash_time = 1000; // text caret flash time
482int QApplicationPrivate::mouse_double_click_time = 400; // mouse dbl click limit
483int QApplicationPrivate::keyboard_input_time = 400; // keyboard input interval
484#ifndef QT_NO_WHEELEVENT
485int QApplicationPrivate::wheel_scroll_lines; // number of lines to scroll
486#endif
487bool qt_is_gui_used;
488bool Q_GUI_EXPORT qt_tab_all_widgets = true;
489bool qt_in_tab_key_event = false;
490int qt_antialiasing_threshold = -1;
491static int drag_time = 500;
492#ifndef QT_GUI_DRAG_DISTANCE
493#define QT_GUI_DRAG_DISTANCE 4
494#endif
495#ifdef Q_OS_SYMBIAN
496// The screens are a bit too small to for your thumb when using only 4 pixels drag distance.
497static int drag_distance = 12; //XXX move to qplatformdefs.h
498#else
499static int drag_distance = QT_GUI_DRAG_DISTANCE;
500#endif
501static Qt::LayoutDirection layout_direction = Qt::LeftToRight;
502QSize QApplicationPrivate::app_strut = QSize(0,0); // no default application strut
503bool QApplicationPrivate::animate_ui = true;
504bool QApplicationPrivate::animate_menu = false;
505bool QApplicationPrivate::fade_menu = false;
506bool QApplicationPrivate::animate_combo = false;
507bool QApplicationPrivate::animate_tooltip = false;
508bool QApplicationPrivate::fade_tooltip = false;
509bool QApplicationPrivate::animate_toolbox = false;
510bool QApplicationPrivate::widgetCount = false;
511bool QApplicationPrivate::load_testability = false;
512#ifdef QT_KEYPAD_NAVIGATION
513# ifdef Q_OS_SYMBIAN
514Qt::NavigationMode QApplicationPrivate::navigationMode = Qt::NavigationModeKeypadDirectional;
515# else
516Qt::NavigationMode QApplicationPrivate::navigationMode = Qt::NavigationModeKeypadTabOrder;
517# endif
518QWidget *QApplicationPrivate::oldEditFocus = 0;
519#endif
520
521bool qt_tabletChokeMouse = false;
522static bool force_reverse = false;
523
524inline bool QApplicationPrivate::isAlien(QWidget *widget)
525{
526 if (!widget)
527 return false;
528#if defined(Q_WS_QWS) || defined(Q_WS_QPA)
529 return !widget->isWindow()
530# ifdef Q_BACKINGSTORE_SUBSURFACES
531 && !(widget->d_func()->maybeTopData() && widget->d_func()->maybeTopData()->windowSurface)
532# endif
533 ;
534#else
535 return !widget->internalWinId();
536#endif
537}
538
539// ######## move to QApplicationPrivate
540// Default application palettes and fonts (per widget type)
541Q_GLOBAL_STATIC(PaletteHash, app_palettes)
542PaletteHash *qt_app_palettes_hash()
543{
544 return app_palettes();
545}
546
547Q_GLOBAL_STATIC(FontHash, app_fonts)
548FontHash *qt_app_fonts_hash()
549{
550 return app_fonts();
551}
552
553QWidgetList *QApplicationPrivate::popupWidgets = 0; // has keyboard input focus
554
555QDesktopWidget *qt_desktopWidget = 0; // root window widgets
556#ifndef QT_NO_CLIPBOARD
557QClipboard *qt_clipboard = 0; // global clipboard object
558#endif
559QWidgetList * qt_modal_stack=0; // stack of modal widgets
560
561/*!
562 \internal
563*/
564void QApplicationPrivate::process_cmdline()
565{
566 // process platform-indep command line
567 if (!qt_is_gui_used || !argc)
568 return;
569
570 int i, j;
571
572 j = 1;
573 for (i=1; i<argc; i++) { // if you add anything here, modify QCoreApplication::arguments()
574 if (argv[i] && *argv[i] != '-') {
575 argv[j++] = argv[i];
576 continue;
577 }
578 QByteArray arg = argv[i];
579 arg = arg;
580 QString s;
581 if (arg == "-qdevel" || arg == "-qdebug") {
582 // obsolete argument
583 } else if (arg.indexOf("-style=", 0) != -1) {
584 s = QString::fromLocal8Bit(arg.right(arg.length() - 7).toLower());
585 } else if (arg == "-style" && i < argc-1) {
586 s = QString::fromLocal8Bit(argv[++i]).toLower();
587#ifndef QT_NO_SESSIONMANAGER
588 } else if (arg == "-session" && i < argc-1) {
589 ++i;
590 if (argv[i] && *argv[i]) {
591 session_id = QString::fromLatin1(argv[i]);
592 int p = session_id.indexOf(QLatin1Char('_'));
593 if (p >= 0) {
594 session_key = session_id.mid(p +1);
595 session_id = session_id.left(p);
596 }
597 is_session_restored = true;
598 }
599#endif
600#ifndef QT_NO_STYLE_STYLESHEET
601 } else if (arg == "-stylesheet" && i < argc -1) {
602 styleSheet = QLatin1String("file:///");
603 styleSheet.append(QString::fromLocal8Bit(argv[++i]));
604 } else if (arg.indexOf("-stylesheet=") != -1) {
605 styleSheet = QLatin1String("file:///");
606 styleSheet.append(QString::fromLocal8Bit(arg.right(arg.length() - 12)));
607#endif
608 } else if (qstrcmp(arg, "-reverse") == 0) {
609 force_reverse = true;
610 QApplication::setLayoutDirection(Qt::RightToLeft);
611 } else if (qstrcmp(arg, "-widgetcount") == 0) {
612 widgetCount = true;
613 } else if (qstrcmp(arg, "-testability") == 0) {
614 load_testability = true;
615 } else if (arg == "-graphicssystem" && i < argc-1) {
616 graphics_system_name = QString::fromLocal8Bit(argv[++i]);
617 } else {
618 argv[j++] = argv[i];
619 }
620 if (!s.isEmpty()) {
621 if (app_style) {
622 delete app_style;
623 app_style = 0;
624 }
625 styleOverride = s;
626 }
627 }
628
629 if(j < argc) {
630 argv[j] = 0;
631 argc = j;
632 }
633}
634
635/*!
636 Initializes the window system and constructs an application object with
637 \a argc command line arguments in \a argv.
638
639 \warning The data referred to by \a argc and \a argv must stay valid for
640 the entire lifetime of the QApplication object. In addition, \a argc must
641 be greater than zero and \a argv must contain at least one valid character
642 string.
643
644 The global \c qApp pointer refers to this application object. Only one
645 application object should be created.
646
647 This application object must be constructed before any \l{QPaintDevice}
648 {paint devices} (including widgets, pixmaps, bitmaps etc.).
649
650 \note \a argc and \a argv might be changed as Qt removes command line
651 arguments that it recognizes.
652
653 Qt debugging options (not available if Qt was compiled without the QT_DEBUG
654 flag defined):
655 \list
656 \o -nograb, tells Qt that it must never grab the mouse or the
657 keyboard.
658 \o -dograb (only under X11), running under a debugger can cause an
659 implicit -nograb, use -dograb to override.
660 \o -sync (only under X11), switches to synchronous mode for
661 debugging.
662 \endlist
663
664 See \l{Debugging Techniques} for a more detailed explanation.
665
666 All Qt programs automatically support the following command line options:
667 \list
668 \o -style= \e style, sets the application GUI style. Possible values
669 are \c motif, \c windows, and \c platinum. If you compiled Qt with
670 additional styles or have additional styles as plugins these will
671 be available to the \c -style command line option.
672 \o -style \e style, is the same as listed above.
673 \o -stylesheet= \e stylesheet, sets the application \l styleSheet. The
674 value must be a path to a file that contains the Style Sheet.
675 \note Relative URLs in the Style Sheet file are relative to the
676 Style Sheet file's path.
677 \o -stylesheet \e stylesheet, is the same as listed above.
678 \o -session= \e session, restores the application from an earlier
679 \l{Session Management}{session}.
680 \o -session \e session, is the same as listed above.
681 \o -widgetcount, prints debug message at the end about number of
682 widgets left undestroyed and maximum number of widgets existed at
683 the same time
684 \o -reverse, sets the application's layout direction to
685 Qt::RightToLeft
686 \o -graphicssystem, sets the backend to be used for on-screen widgets
687 and QPixmaps. Available options are \c{raster} and \c{opengl}.
688 \o -qmljsdebugger=, activates the QML/JS debugger with a specified port.
689 The value must be of format port:1234[,block], where block is optional
690 and will make the application wait until a debugger connects to it.
691 \endlist
692
693 The X11 version of Qt supports some traditional X11 command line options:
694 \list
695 \o -display \e display, sets the X display (default is $DISPLAY).
696 \o -geometry \e geometry, sets the client geometry of the first window
697 that is shown.
698 \o -fn or \c -font \e font, defines the application font. The font
699 should be specified using an X logical font description. Note that
700 this option is ignored when Qt is built with fontconfig support enabled.
701 \o -bg or \c -background \e color, sets the default background color
702 and an application palette (light and dark shades are calculated).
703 \o -fg or \c -foreground \e color, sets the default foreground color.
704 \o -btn or \c -button \e color, sets the default button color.
705 \o -name \e name, sets the application name.
706 \o -title \e title, sets the application title.
707 \o -visual \c TrueColor, forces the application to use a TrueColor
708 visual on an 8-bit display.
709 \o -ncols \e count, limits the number of colors allocated in the color
710 cube on an 8-bit display, if the application is using the
711 QApplication::ManyColor color specification. If \e count is 216
712 then a 6x6x6 color cube is used (i.e. 6 levels of red, 6 of green,
713 and 6 of blue); for other values, a cube approximately proportional
714 to a 2x3x1 cube is used.
715 \o -cmap, causes the application to install a private color map on an
716 8-bit display.
717 \o -im, sets the input method server (equivalent to setting the
718 XMODIFIERS environment variable)
719 \o -inputstyle, defines how the input is inserted into the given
720 widget, e.g., \c onTheSpot makes the input appear directly in the
721 widget, while \c overTheSpot makes the input appear in a box
722 floating over the widget and is not inserted until the editing is
723 done.
724 \endlist
725
726 \section1 X11 Notes
727
728 If QApplication fails to open the X11 display, it will terminate
729 the process. This behavior is consistent with most X11
730 applications.
731
732 \sa arguments()
733*/
734
735QApplication::QApplication(int &argc, char **argv)
736 : QCoreApplication(*new QApplicationPrivate(argc, argv, GuiClient, 0x040000))
737{ Q_D(QApplication); d->construct(); }
738
739QApplication::QApplication(int &argc, char **argv, int _internal)
740 : QCoreApplication(*new QApplicationPrivate(argc, argv, GuiClient, _internal))
741{ Q_D(QApplication); d->construct(); }
742
743
744/*!
745 Constructs an application object with \a argc command line arguments in
746 \a argv. If \a GUIenabled is true, a GUI application is constructed,
747 otherwise a non-GUI (console) application is created.
748
749 \warning The data referred to by \a argc and \a argv must stay valid for
750 the entire lifetime of the QApplication object. In addition, \a argc must
751 be greater than zero and \a argv must contain at least one valid character
752 string.
753
754 Set \a GUIenabled to false for programs without a graphical user interface
755 that should be able to run without a window system.
756
757 On X11, the window system is initialized if \a GUIenabled is true. If
758 \a GUIenabled is false, the application does not connect to the X server.
759 On Windows and Mac OS, currently the window system is always initialized,
760 regardless of the value of GUIenabled. This may change in future versions
761 of Qt.
762
763 The following example shows how to create an application that uses a
764 graphical interface when available.
765
766 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 0
767*/
768
769QApplication::QApplication(int &argc, char **argv, bool GUIenabled )
770 : QCoreApplication(*new QApplicationPrivate(argc, argv, GUIenabled ? GuiClient : Tty, 0x040000))
771{ Q_D(QApplication); d->construct(); }
772
773QApplication::QApplication(int &argc, char **argv, bool GUIenabled , int _internal)
774 : QCoreApplication(*new QApplicationPrivate(argc, argv, GUIenabled ? GuiClient : Tty, _internal))
775{ Q_D(QApplication); d->construct();}
776
777
778
779/*!
780 Constructs an application object with \a argc command line arguments in
781 \a argv.
782
783 \warning The data referred to by \a argc and \a argv must stay valid for
784 the entire lifetime of the QApplication object. In addition, \a argc must
785 be greater than zero and \a argv must contain at least one valid character
786 string.
787
788 With Qt for Embedded Linux, passing QApplication::GuiServer for \a type
789 makes this application the server (equivalent to running with the
790 \c -qws option).
791*/
792QApplication::QApplication(int &argc, char **argv, Type type)
793 : QCoreApplication(*new QApplicationPrivate(argc, argv, type, 0x040000))
794{ Q_D(QApplication); d->construct(); }
795
796QApplication::QApplication(int &argc, char **argv, Type type , int _internal)
797 : QCoreApplication(*new QApplicationPrivate(argc, argv, type, _internal))
798{ Q_D(QApplication); d->construct(); }
799
800#if defined(Q_WS_X11) && !defined(QT_NO_EGL)
801static int qt_matchLibraryName(dl_phdr_info *info, size_t, void *data)
802{
803 const char *name = static_cast<const char *>(data);
804 return strstr(info->dlpi_name, name) != 0;
805}
806#endif
807
808/*!
809 \internal
810*/
811void QApplicationPrivate::construct(
812#ifdef Q_WS_X11
813 Display *dpy, Qt::HANDLE visual, Qt::HANDLE cmap
814#endif
815 )
816{
817 initResources();
818
819 qt_is_gui_used = (qt_appType != QApplication::Tty);
820 process_cmdline();
821 // the environment variable has the lowest precedence of runtime graphicssystem switches
822 if (graphics_system_name.isEmpty())
823 graphics_system_name = QString::fromLocal8Bit(qgetenv("QT_GRAPHICSSYSTEM"));
824
825#if defined(Q_WS_X11) && !defined(QT_NO_EGL)
826 if (graphics_system_name.isEmpty()) {
827 bool linksWithMeeGoTouch = dl_iterate_phdr(qt_matchLibraryName, const_cast<char *>("libmeegotouchcore"));
828 bool linksWithMeeGoGraphicsSystemHelper = dl_iterate_phdr(qt_matchLibraryName, const_cast<char *>("libQtMeeGoGraphicsSystemHelper"));
829
830 if (linksWithMeeGoTouch && !linksWithMeeGoGraphicsSystemHelper) {
831 qWarning("Running non-meego graphics system enabled MeeGo touch, forcing native graphicssystem\n");
832 graphics_system_name = QLatin1String("native");
833 }
834 }
835#endif
836
837 // Must be called before initialize()
838 qt_init(this, qt_appType
839#ifdef Q_WS_X11
840 , dpy, visual, cmap
841#endif
842 );
843 initialize();
844 eventDispatcher->startingUp();
845
846#ifdef QT_EVAL
847 extern void qt_gui_eval_init(uint);
848 qt_gui_eval_init(application_type);
849#endif
850
851#if defined(Q_OS_SYMBIAN) && !defined(QT_NO_SYSTEMLOCALE)
852 symbianInit();
853#endif
854
855#ifndef QT_NO_LIBRARY
856 if(load_testability) {
857 QLibrary testLib(QLatin1String("qttestability"));
858 if (testLib.load()) {
859 typedef void (*TasInitialize)(void);
860 TasInitialize initFunction = (TasInitialize)testLib.resolve("qt_testability_init");
861#ifdef Q_OS_SYMBIAN
862 // resolving method by name does not work on Symbian OS so need to use ordinal
863 if(!initFunction) {
864 initFunction = (TasInitialize)testLib.resolve("1");
865 }
866#endif
867 if (initFunction) {
868 initFunction();
869 } else {
870 qCritical("Library qttestability resolve failed!");
871 }
872 } else {
873 qCritical("Library qttestability load failed!");
874 }
875 }
876
877 //make sure the plugin is loaded
878 if (qt_is_gui_used)
879 qt_guiPlatformPlugin();
880#endif
881
882#ifdef Q_OS_SYMBIAN
883 symbianHandleLiteModeStartup();
884#endif
885}
886
887#if defined(Q_WS_X11)
888// ### a string literal is a cont char*
889// ### using it as a char* is wrong and could lead to segfaults
890// ### if aargv is modified someday
891// ########## make it work with argc == argv == 0
892static int aargc = 1;
893static char *aargv[] = { (char*)"unknown", 0 };
894
895/*!
896 \fn QApplication::QApplication(Display* display, Qt::HANDLE visual, Qt::HANDLE colormap)
897
898 Creates an application, given an already open display \a display. If
899 \a visual and \a colormap are non-zero, the application will use those
900 values as the default Visual and Colormap contexts.
901
902 \warning Qt only supports TrueColor visuals at depths higher than 8
903 bits-per-pixel.
904
905 This function is only available on X11.
906*/
907QApplication::QApplication(Display* dpy, Qt::HANDLE visual, Qt::HANDLE colormap)
908 : QCoreApplication(*new QApplicationPrivate(aargc, aargv, GuiClient, 0x040000))
909{
910 if (! dpy)
911 qWarning("QApplication: Invalid Display* argument");
912 Q_D(QApplication);
913 d->construct(dpy, visual, colormap);
914}
915
916QApplication::QApplication(Display* dpy, Qt::HANDLE visual, Qt::HANDLE colormap, int _internal)
917 : QCoreApplication(*new QApplicationPrivate(aargc, aargv, GuiClient, _internal))
918{
919 if (! dpy)
920 qWarning("QApplication: Invalid Display* argument");
921 Q_D(QApplication);
922 d->construct(dpy, visual, colormap);
923 QApplicationPrivate::app_compile_version = _internal;
924}
925
926/*!
927 \fn QApplication::QApplication(Display *display, int &argc, char **argv,
928 Qt::HANDLE visual, Qt::HANDLE colormap)
929
930 Creates an application, given an already open \a display and using \a argc
931 command line arguments in \a argv. If \a visual and \a colormap are
932 non-zero, the application will use those values as the default Visual
933 and Colormap contexts.
934
935 \warning Qt only supports TrueColor visuals at depths higher than 8
936 bits-per-pixel.
937
938 This function is only available on X11.
939*/
940QApplication::QApplication(Display *dpy, int &argc, char **argv,
941 Qt::HANDLE visual, Qt::HANDLE colormap)
942 : QCoreApplication(*new QApplicationPrivate(argc, argv, GuiClient, 0x040000))
943{
944 if (! dpy)
945 qWarning("QApplication: Invalid Display* argument");
946 Q_D(QApplication);
947 d->construct(dpy, visual, colormap);
948}
949
950QApplication::QApplication(Display *dpy, int &argc, char **argv,
951 Qt::HANDLE visual, Qt::HANDLE colormap, int _internal)
952 : QCoreApplication(*new QApplicationPrivate(argc, argv, GuiClient, _internal))
953{
954 if (! dpy)
955 qWarning("QApplication: Invalid Display* argument");
956 Q_D(QApplication);
957 d->construct(dpy, visual, colormap);
958 QApplicationPrivate::app_compile_version = _internal;
959}
960
961#endif // Q_WS_X11
962
963extern void qInitDrawhelperAsm();
964extern void qInitImageConversions();
965extern int qRegisterGuiVariant();
966extern int qUnregisterGuiVariant();
967#ifndef QT_NO_STATEMACHINE
968extern int qRegisterGuiStateMachine();
969extern int qUnregisterGuiStateMachine();
970#endif
971
972/*!
973 \fn void QApplicationPrivate::initialize()
974
975 Initializes the QApplication object, called from the constructors.
976*/
977void QApplicationPrivate::initialize()
978{
979 QWidgetPrivate::mapper = new QWidgetMapper;
980 QWidgetPrivate::allWidgets = new QWidgetSet;
981
982#if !defined(Q_WS_X11) && !defined(Q_WS_QWS) && !defined(Q_WS_QPA)
983 // initialize the graphics system - on X11 this is initialized inside
984 // qt_init() in qapplication_x11.cpp because of several reasons.
985 // On QWS, the graphics system is set by the QScreen plugin.
986 // We don't use graphics systems in Qt QPA
987 graphics_system = QGraphicsSystemFactory::create(graphics_system_name);
988#endif
989
990 if (qt_appType != QApplication::Tty)
991 (void) QApplication::style(); // trigger creation of application style
992 // trigger registering of QVariant's GUI types
993 qRegisterGuiVariant();
994#ifndef QT_NO_STATEMACHINE
995 // trigger registering of QStateMachine's GUI types
996 qRegisterGuiStateMachine();
997#endif
998
999 is_app_running = true; // no longer starting up
1000
1001 Q_Q(QApplication);
1002#ifndef QT_NO_SESSIONMANAGER
1003 // connect to the session manager
1004 session_manager = new QSessionManager(q, session_id, session_key);
1005#endif
1006
1007 if (qgetenv("QT_USE_NATIVE_WINDOWS").toInt() > 0)
1008 q->setAttribute(Qt::AA_NativeWindows);
1009
1010#ifdef Q_WS_WINCE
1011#ifdef QT_AUTO_MAXIMIZE_THRESHOLD
1012 autoMaximizeThreshold = QT_AUTO_MAXIMIZE_THRESHOLD;
1013#else
1014 if (qt_wince_is_mobile())
1015 autoMaximizeThreshold = 50;
1016 else
1017 autoMaximizeThreshold = -1;
1018#endif //QT_AUTO_MAXIMIZE_THRESHOLD
1019#endif //Q_WS_WINCE
1020
1021 // Set up which span functions should be used in raster engine...
1022 qInitDrawhelperAsm();
1023 // and QImage conversion functions
1024 qInitImageConversions();
1025
1026#ifndef QT_NO_WHEELEVENT
1027 QApplicationPrivate::wheel_scroll_lines = 3;
1028#endif
1029
1030#ifdef Q_WS_S60
1031 q->setAttribute(Qt::AA_S60DisablePartialScreenInputMode);
1032#endif
1033
1034 if (qt_is_gui_used)
1035 initializeMultitouch();
1036}
1037
1038/*!
1039 Returns the type of application (\l Tty, GuiClient, or
1040 GuiServer). The type is set when constructing the QApplication
1041 object.
1042*/
1043QApplication::Type QApplication::type()
1044{
1045 return qt_appType;
1046}
1047
1048/*****************************************************************************
1049 Functions returning the active popup and modal widgets.
1050 *****************************************************************************/
1051
1052/*!
1053 Returns the active popup widget.
1054
1055 A popup widget is a special top-level widget that sets the \c
1056 Qt::WType_Popup widget flag, e.g. the QMenu widget. When the application
1057 opens a popup widget, all events are sent to the popup. Normal widgets and
1058 modal widgets cannot be accessed before the popup widget is closed.
1059
1060 Only other popup widgets may be opened when a popup widget is shown. The
1061 popup widgets are organized in a stack. This function returns the active
1062 popup widget at the top of the stack.
1063
1064 \sa activeModalWidget(), topLevelWidgets()
1065*/
1066
1067QWidget *QApplication::activePopupWidget()
1068{
1069 return QApplicationPrivate::popupWidgets && !QApplicationPrivate::popupWidgets->isEmpty() ?
1070 QApplicationPrivate::popupWidgets->last() : 0;
1071}
1072
1073
1074/*!
1075 Returns the active modal widget.
1076
1077 A modal widget is a special top-level widget which is a subclass of QDialog
1078 that specifies the modal parameter of the constructor as true. A modal
1079 widget must be closed before the user can continue with other parts of the
1080 program.
1081
1082 Modal widgets are organized in a stack. This function returns the active
1083 modal widget at the top of the stack.
1084
1085 \sa activePopupWidget(), topLevelWidgets()
1086*/
1087
1088QWidget *QApplication::activeModalWidget()
1089{
1090 return qt_modal_stack && !qt_modal_stack->isEmpty() ? qt_modal_stack->first() : 0;
1091}
1092
1093/*!
1094 Cleans up any window system resources that were allocated by this
1095 application. Sets the global variable \c qApp to 0.
1096*/
1097
1098QApplication::~QApplication()
1099{
1100 Q_D(QApplication);
1101
1102#ifndef QT_NO_CLIPBOARD
1103 // flush clipboard contents
1104 if (qt_clipboard) {
1105 QEvent event(QEvent::Clipboard);
1106 QApplication::sendEvent(qt_clipboard, &event);
1107 }
1108#endif
1109
1110 //### this should probable be done even later
1111 qt_call_post_routines();
1112
1113 // kill timers before closing down the dispatcher
1114 d->toolTipWakeUp.stop();
1115 d->toolTipFallAsleep.stop();
1116
1117 d->eventDispatcher->closingDown();
1118 d->eventDispatcher = 0;
1119 QApplicationPrivate::is_app_closing = true;
1120 QApplicationPrivate::is_app_running = false;
1121
1122 delete QWidgetPrivate::mapper;
1123 QWidgetPrivate::mapper = 0;
1124
1125 // delete all widgets
1126 if (QWidgetPrivate::allWidgets) {
1127 QWidgetSet *mySet = QWidgetPrivate::allWidgets;
1128 QWidgetPrivate::allWidgets = 0;
1129 for (QWidgetSet::ConstIterator it = mySet->constBegin(); it != mySet->constEnd(); ++it) {
1130 register QWidget *w = *it;
1131 if (!w->parent()) // window
1132 w->destroy(true, true);
1133 }
1134 delete mySet;
1135 }
1136
1137 delete qt_desktopWidget;
1138 qt_desktopWidget = 0;
1139
1140#ifndef QT_NO_CLIPBOARD
1141 delete qt_clipboard;
1142 qt_clipboard = 0;
1143#endif
1144
1145#if defined(Q_WS_X11) || defined(Q_WS_WIN)
1146 delete d->move_cursor; d->move_cursor = 0;
1147 delete d->copy_cursor; d->copy_cursor = 0;
1148 delete d->link_cursor; d->link_cursor = 0;
1149#endif
1150#if defined(Q_WS_WIN)
1151 delete d->ignore_cursor; d->ignore_cursor = 0;
1152#endif
1153
1154 delete QApplicationPrivate::app_pal;
1155 QApplicationPrivate::app_pal = 0;
1156 delete QApplicationPrivate::sys_pal;
1157 QApplicationPrivate::sys_pal = 0;
1158 delete QApplicationPrivate::set_pal;
1159 QApplicationPrivate::set_pal = 0;
1160 app_palettes()->clear();
1161
1162 {
1163 QMutexLocker locker(applicationFontMutex());
1164 delete QApplicationPrivate::app_font;
1165 QApplicationPrivate::app_font = 0;
1166 }
1167 delete QApplicationPrivate::sys_font;
1168 QApplicationPrivate::sys_font = 0;
1169 delete QApplicationPrivate::set_font;
1170 QApplicationPrivate::set_font = 0;
1171 app_fonts()->clear();
1172
1173 delete QApplicationPrivate::app_style;
1174 QApplicationPrivate::app_style = 0;
1175 delete QApplicationPrivate::app_icon;
1176 QApplicationPrivate::app_icon = 0;
1177 delete QApplicationPrivate::graphics_system;
1178 QApplicationPrivate::graphics_system = 0;
1179#ifndef QT_NO_CURSOR
1180 d->cursor_list.clear();
1181#endif
1182
1183#ifndef QT_NO_DRAGANDDROP
1184 if (qt_is_gui_used)
1185 delete QDragManager::self();
1186#endif
1187
1188 d->cleanupMultitouch();
1189
1190 qt_cleanup();
1191
1192 if (QApplicationPrivate::widgetCount)
1193 qDebug("Widgets left: %i Max widgets: %i \n", QWidgetPrivate::instanceCounter, QWidgetPrivate::maxInstances);
1194#ifndef QT_NO_SESSIONMANAGER
1195 delete d->session_manager;
1196 d->session_manager = 0;
1197#endif //QT_NO_SESSIONMANAGER
1198
1199 QApplicationPrivate::obey_desktop_settings = true;
1200 QApplicationPrivate::cursor_flash_time = 1000;
1201 QApplicationPrivate::mouse_double_click_time = 400;
1202 QApplicationPrivate::keyboard_input_time = 400;
1203
1204 drag_time = 500;
1205 drag_distance = 4;
1206 layout_direction = Qt::LeftToRight;
1207 QApplicationPrivate::app_strut = QSize(0, 0);
1208 QApplicationPrivate::animate_ui = true;
1209 QApplicationPrivate::animate_menu = false;
1210 QApplicationPrivate::fade_menu = false;
1211 QApplicationPrivate::animate_combo = false;
1212 QApplicationPrivate::animate_tooltip = false;
1213 QApplicationPrivate::fade_tooltip = false;
1214 QApplicationPrivate::widgetCount = false;
1215
1216#ifndef QT_NO_STATEMACHINE
1217 // trigger unregistering of QStateMachine's GUI types
1218 qUnregisterGuiStateMachine();
1219#endif
1220 // trigger unregistering of QVariant's GUI types
1221 qUnregisterGuiVariant();
1222}
1223
1224
1225/*!
1226 \fn QWidget *QApplication::widgetAt(const QPoint &point)
1227
1228 Returns the widget at global screen position \a point, or 0 if there is no
1229 Qt widget there.
1230
1231 This function can be slow.
1232
1233 \sa QCursor::pos(), QWidget::grabMouse(), QWidget::grabKeyboard()
1234*/
1235QWidget *QApplication::widgetAt(const QPoint &p)
1236{
1237 QWidget *window = QApplication::topLevelAt(p);
1238 if (!window)
1239 return 0;
1240
1241 QWidget *child = 0;
1242
1243 if (!window->testAttribute(Qt::WA_TransparentForMouseEvents))
1244 child = window->childAt(window->mapFromGlobal(p));
1245
1246 if (child)
1247 return child;
1248
1249 if (window->testAttribute(Qt::WA_TransparentForMouseEvents)) {
1250 //shoot a hole in the widget and try once again,
1251 //suboptimal on Qt for Embedded Linux where we do
1252 //know the stacking order of the toplevels.
1253 int x = p.x();
1254 int y = p.y();
1255 QRegion oldmask = window->mask();
1256 QPoint wpoint = window->mapFromGlobal(QPoint(x, y));
1257 QRegion newmask = (oldmask.isEmpty() ? QRegion(window->rect()) : oldmask)
1258 - QRegion(wpoint.x(), wpoint.y(), 1, 1);
1259 window->setMask(newmask);
1260 QWidget *recurse = 0;
1261 if (QApplication::topLevelAt(p) != window) // verify recursion will terminate
1262 recurse = widgetAt(x, y);
1263 if (oldmask.isEmpty())
1264 window->clearMask();
1265 else
1266 window->setMask(oldmask);
1267 return recurse;
1268 }
1269 return window;
1270}
1271
1272/*!
1273 \fn QWidget *QApplication::widgetAt(int x, int y)
1274
1275 \overload
1276
1277 Returns the widget at global screen position (\a x, \a y), or 0 if there is
1278 no Qt widget there.
1279*/
1280
1281/*!
1282 \fn void QApplication::setArgs(int argc, char **argv)
1283 \internal
1284*/
1285
1286
1287
1288/*!
1289 \internal
1290*/
1291bool QApplication::compressEvent(QEvent *event, QObject *receiver, QPostEventList *postedEvents)
1292{
1293 if ((event->type() == QEvent::UpdateRequest
1294#ifdef QT3_SUPPORT
1295 || event->type() == QEvent::LayoutHint
1296#endif
1297 || event->type() == QEvent::LayoutRequest
1298 || event->type() == QEvent::Resize
1299 || event->type() == QEvent::Move
1300 || event->type() == QEvent::LanguageChange
1301 || event->type() == QEvent::UpdateSoftKeys
1302 || event->type() == QEvent::InputMethod)) {
1303 for (QPostEventList::const_iterator it = postedEvents->constBegin(); it != postedEvents->constEnd(); ++it) {
1304 const QPostEvent &cur = *it;
1305 if (cur.receiver != receiver || cur.event == 0 || cur.event->type() != event->type())
1306 continue;
1307 if (cur.event->type() == QEvent::LayoutRequest
1308#ifdef QT3_SUPPORT
1309 || cur.event->type() == QEvent::LayoutHint
1310#endif
1311 || cur.event->type() == QEvent::UpdateRequest) {
1312 ;
1313 } else if (cur.event->type() == QEvent::Resize) {
1314 ((QResizeEvent *)(cur.event))->s = ((QResizeEvent *)event)->s;
1315 } else if (cur.event->type() == QEvent::Move) {
1316 ((QMoveEvent *)(cur.event))->p = ((QMoveEvent *)event)->p;
1317 } else if (cur.event->type() == QEvent::LanguageChange) {
1318 ;
1319 } else if (cur.event->type() == QEvent::UpdateSoftKeys) {
1320 ;
1321 } else if ( cur.event->type() == QEvent::InputMethod ) {
1322 *(QInputMethodEvent *)(cur.event) = *(QInputMethodEvent *)event;
1323 } else {
1324 continue;
1325 }
1326 delete event;
1327 return true;
1328 }
1329 return false;
1330 }
1331 return QCoreApplication::compressEvent(event, receiver, postedEvents);
1332}
1333
1334/*!
1335 \property QApplication::styleSheet
1336 \brief the application style sheet
1337 \since 4.2
1338
1339 By default, this property returns an empty string unless the user specifies
1340 the \c{-stylesheet} option on the command line when running the application.
1341
1342 \sa QWidget::setStyle(), {Qt Style Sheets}
1343*/
1344
1345/*!
1346 \property QApplication::autoMaximizeThreshold
1347 \since 4.4
1348 \brief defines a threshold for auto maximizing widgets
1349
1350 \bold{The auto maximize threshold is only available as part of Qt for
1351 Windows CE.}
1352
1353 This property defines a threshold for the size of a window as a percentage
1354 of the screen size. If the minimum size hint of a window exceeds the
1355 threshold, calling show() will cause the window to be maximized
1356 automatically.
1357
1358 Setting the threshold to 100 or greater means that the widget will always
1359 be maximized. Alternatively, setting the threshold to 50 means that the
1360 widget will be maximized only if the vertical minimum size hint is at least
1361 50% of the vertical screen size.
1362
1363 Setting the threshold to -1 disables the feature.
1364
1365 On Windows CE the default is -1 (i.e., it is disabled).
1366 On Windows Mobile the default is 40.
1367*/
1368
1369/*!
1370 \property QApplication::autoSipEnabled
1371 \since 4.5
1372 \brief toggles automatic SIP (software input panel) visibility
1373
1374 Set this property to \c true to automatically display the SIP when entering
1375 widgets that accept keyboard input. This property only affects widgets with
1376 the WA_InputMethodEnabled attribute set, and is typically used to launch
1377 a virtual keyboard on devices which have very few or no keys.
1378
1379 \bold{ The property only has an effect on platforms which use software input
1380 panels, such as Windows CE and Symbian.}
1381
1382 The default is platform dependent.
1383*/
1384
1385#ifdef Q_WS_WINCE
1386void QApplication::setAutoMaximizeThreshold(const int threshold)
1387{
1388 QApplicationPrivate::autoMaximizeThreshold = threshold;
1389}
1390
1391int QApplication::autoMaximizeThreshold() const
1392{
1393 return QApplicationPrivate::autoMaximizeThreshold;
1394}
1395#endif
1396
1397void QApplication::setAutoSipEnabled(const bool enabled)
1398{
1399 QApplicationPrivate::autoSipEnabled = enabled;
1400}
1401
1402bool QApplication::autoSipEnabled() const
1403{
1404 return QApplicationPrivate::autoSipEnabled;
1405}
1406
1407#ifndef QT_NO_STYLE_STYLESHEET
1408
1409QString QApplication::styleSheet() const
1410{
1411 return QApplicationPrivate::styleSheet;
1412}
1413
1414void QApplication::setStyleSheet(const QString& styleSheet)
1415{
1416 QApplicationPrivate::styleSheet = styleSheet;
1417 QStyleSheetStyle *proxy = qobject_cast<QStyleSheetStyle*>(QApplicationPrivate::app_style);
1418 if (styleSheet.isEmpty()) { // application style sheet removed
1419 if (!proxy)
1420 return; // there was no stylesheet before
1421 setStyle(proxy->base);
1422 } else if (proxy) { // style sheet update, just repolish
1423 proxy->repolish(qApp);
1424 } else { // stylesheet set the first time
1425 QStyleSheetStyle *newProxy = new QStyleSheetStyle(QApplicationPrivate::app_style);
1426 QApplicationPrivate::app_style->setParent(newProxy);
1427 setStyle(newProxy);
1428 }
1429}
1430
1431#endif // QT_NO_STYLE_STYLESHEET
1432
1433/*!
1434 Returns the application's style object.
1435
1436 \sa setStyle(), QStyle
1437*/
1438QStyle *QApplication::style()
1439{
1440 if (QApplicationPrivate::app_style)
1441 return QApplicationPrivate::app_style;
1442 if (!qt_is_gui_used) {
1443 Q_ASSERT(!"No style available in non-gui applications!");
1444 return 0;
1445 }
1446
1447 if (!QApplicationPrivate::app_style) {
1448 // Compile-time search for default style
1449 //
1450 QString style;
1451#ifdef QT_BUILD_INTERNAL
1452 QString envStyle = QString::fromLocal8Bit(qgetenv("QT_STYLE_OVERRIDE"));
1453#else
1454 QString envStyle;
1455#endif
1456 if (!QApplicationPrivate::styleOverride.isEmpty()) {
1457 style = QApplicationPrivate::styleOverride;
1458 } else if (!envStyle.isEmpty()) {
1459 style = envStyle;
1460 } else {
1461 style = QApplicationPrivate::desktopStyleKey();
1462 }
1463
1464 QStyle *&app_style = QApplicationPrivate::app_style;
1465 app_style = QStyleFactory::create(style);
1466 if (!app_style) {
1467 QStringList styles = QStyleFactory::keys();
1468 for (int i = 0; i < styles.size(); ++i) {
1469 if ((app_style = QStyleFactory::create(styles.at(i))))
1470 break;
1471 }
1472 }
1473 if (!app_style) {
1474 Q_ASSERT(!"No styles available!");
1475 return 0;
1476 }
1477 }
1478 // take ownership of the style
1479 QApplicationPrivate::app_style->setParent(qApp);
1480
1481 if (!QApplicationPrivate::sys_pal)
1482 QApplicationPrivate::setSystemPalette(QApplicationPrivate::app_style->standardPalette());
1483 if (QApplicationPrivate::set_pal) // repolish set palette with the new style
1484 QApplication::setPalette(*QApplicationPrivate::set_pal);
1485
1486#ifndef QT_NO_STYLE_STYLESHEET
1487 if (!QApplicationPrivate::styleSheet.isEmpty()) {
1488 qApp->setStyleSheet(QApplicationPrivate::styleSheet);
1489 } else
1490#endif
1491 QApplicationPrivate::app_style->polish(qApp);
1492
1493 return QApplicationPrivate::app_style;
1494}
1495
1496/*!
1497 Sets the application's GUI style to \a style. Ownership of the style object
1498 is transferred to QApplication, so QApplication will delete the style
1499 object on application exit or when a new style is set and the old style is
1500 still the parent of the application object.
1501
1502 Example usage:
1503 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 1
1504
1505 When switching application styles, the color palette is set back to the
1506 initial colors or the system defaults. This is necessary since certain
1507 styles have to adapt the color palette to be fully style-guide compliant.
1508
1509 Setting the style before a palette has been set, i.e., before creating
1510 QApplication, will cause the application to use QStyle::standardPalette()
1511 for the palette.
1512
1513 \warning Qt style sheets are currently not supported for custom QStyle
1514 subclasses. We plan to address this in some future release.
1515
1516 \sa style(), QStyle, setPalette(), desktopSettingsAware()
1517*/
1518void QApplication::setStyle(QStyle *style)
1519{
1520 if (!style || style == QApplicationPrivate::app_style)
1521 return;
1522
1523 QWidgetList all = allWidgets();
1524
1525 // clean up the old style
1526 if (QApplicationPrivate::app_style) {
1527 if (QApplicationPrivate::is_app_running && !QApplicationPrivate::is_app_closing) {
1528 for (QWidgetList::ConstIterator it = all.constBegin(); it != all.constEnd(); ++it) {
1529 register QWidget *w = *it;
1530 if (!(w->windowType() == Qt::Desktop) && // except desktop
1531 w->testAttribute(Qt::WA_WState_Polished)) { // has been polished
1532 QApplicationPrivate::app_style->unpolish(w);
1533 }
1534 }
1535 }
1536 QApplicationPrivate::app_style->unpolish(qApp);
1537 }
1538
1539 QStyle *old = QApplicationPrivate::app_style; // save
1540
1541#ifndef QT_NO_STYLE_STYLESHEET
1542 if (!QApplicationPrivate::styleSheet.isEmpty() && !qobject_cast<QStyleSheetStyle *>(style)) {
1543 // we have a stylesheet already and a new style is being set
1544 QStyleSheetStyle *newProxy = new QStyleSheetStyle(style);
1545 style->setParent(newProxy);
1546 QApplicationPrivate::app_style = newProxy;
1547 } else
1548#endif // QT_NO_STYLE_STYLESHEET
1549 QApplicationPrivate::app_style = style;
1550 QApplicationPrivate::app_style->setParent(qApp); // take ownership
1551
1552 // take care of possible palette requirements of certain gui
1553 // styles. Do it before polishing the application since the style
1554 // might call QApplication::setPalette() itself
1555 if (QApplicationPrivate::set_pal) {
1556 QApplication::setPalette(*QApplicationPrivate::set_pal);
1557 } else if (QApplicationPrivate::sys_pal) {
1558 QApplicationPrivate::initializeWidgetPaletteHash();
1559 QApplicationPrivate::setPalette_helper(*QApplicationPrivate::sys_pal, /*className=*/0, /*clearWidgetPaletteHash=*/false);
1560 } else if (!QApplicationPrivate::sys_pal) {
1561 // Initialize the sys_pal if it hasn't happened yet...
1562 QApplicationPrivate::setSystemPalette(QApplicationPrivate::app_style->standardPalette());
1563 }
1564
1565 // initialize the application with the new style
1566 QApplicationPrivate::app_style->polish(qApp);
1567
1568 // re-polish existing widgets if necessary
1569 if (QApplicationPrivate::is_app_running && !QApplicationPrivate::is_app_closing) {
1570 for (QWidgetList::ConstIterator it1 = all.constBegin(); it1 != all.constEnd(); ++it1) {
1571 register QWidget *w = *it1;
1572 if (w->windowType() != Qt::Desktop && w->testAttribute(Qt::WA_WState_Polished)) {
1573 if (w->style() == QApplicationPrivate::app_style)
1574 QApplicationPrivate::app_style->polish(w); // repolish
1575#ifndef QT_NO_STYLE_STYLESHEET
1576 else
1577 w->setStyleSheet(w->styleSheet()); // touch
1578#endif
1579 }
1580 }
1581
1582 for (QWidgetList::ConstIterator it2 = all.constBegin(); it2 != all.constEnd(); ++it2) {
1583 register QWidget *w = *it2;
1584 if (w->windowType() != Qt::Desktop && !w->testAttribute(Qt::WA_SetStyle)) {
1585 QEvent e(QEvent::StyleChange);
1586 QApplication::sendEvent(w, &e);
1587#ifdef QT3_SUPPORT
1588 if (old)
1589 w->styleChange(*old);
1590#endif
1591 w->update();
1592 }
1593 }
1594 }
1595
1596#ifndef QT_NO_STYLE_STYLESHEET
1597 if (QStyleSheetStyle *oldProxy = qobject_cast<QStyleSheetStyle *>(old)) {
1598 oldProxy->deref();
1599 } else
1600#endif
1601 if (old && old->parent() == qApp) {
1602 delete old;
1603 }
1604
1605 if (QApplicationPrivate::focus_widget) {
1606 QFocusEvent in(QEvent::FocusIn, Qt::OtherFocusReason);
1607 QApplication::sendEvent(QApplicationPrivate::focus_widget->style(), &in);
1608 QApplicationPrivate::focus_widget->update();
1609 }
1610}
1611
1612/*!
1613 \overload
1614
1615 Requests a QStyle object for \a style from the QStyleFactory.
1616
1617 The string must be one of the QStyleFactory::keys(), typically one of
1618 "windows", "motif", "cde", "plastique", "windowsxp", or "macintosh". Style
1619 names are case insensitive.
1620
1621 Returns 0 if an unknown \a style is passed, otherwise the QStyle object
1622 returned is set as the application's GUI style.
1623
1624 \warning To ensure that the application's style is set correctly, it is
1625 best to call this function before the QApplication constructor, if
1626 possible.
1627*/
1628QStyle* QApplication::setStyle(const QString& style)
1629{
1630 QStyle *s = QStyleFactory::create(style);
1631 if (!s)
1632 return 0;
1633
1634 setStyle(s);
1635 return s;
1636}
1637
1638/*!
1639 \since 4.5
1640
1641 Sets the default graphics backend to \a system, which will be used for
1642 on-screen widgets and QPixmaps. The available systems are \c{"native"},
1643 \c{"raster"} and \c{"opengl"}.
1644
1645 There are several ways to set the graphics backend, in order of decreasing
1646 precedence:
1647 \list
1648 \o the application commandline \c{-graphicssystem} switch
1649 \o QApplication::setGraphicsSystem()
1650 \o the QT_GRAPHICSSYSTEM environment variable
1651 \o the Qt configure \c{-graphicssystem} switch
1652 \endlist
1653 If the highest precedence switch sets an invalid name, the error will be
1654 ignored and the default backend will be used.
1655
1656 \warning This function is only effective before the QApplication constructor
1657 is called.
1658
1659 \note The \c{"opengl"} option is currently experimental.
1660*/
1661
1662void QApplication::setGraphicsSystem(const QString &system)
1663{
1664#ifdef Q_WS_QPA
1665 Q_UNUSED(system);
1666#else
1667# ifdef QT_GRAPHICSSYSTEM_RUNTIME
1668 if (QApplicationPrivate::graphics_system_name == QLatin1String("runtime")) {
1669 QRuntimeGraphicsSystem *r =
1670 static_cast<QRuntimeGraphicsSystem *>(QApplicationPrivate::graphics_system);
1671 r->setGraphicsSystem(system);
1672 } else
1673# endif
1674 QApplicationPrivate::graphics_system_name = system;
1675#endif
1676}
1677
1678/*!
1679 Returns the color specification.
1680
1681 \sa QApplication::setColorSpec()
1682*/
1683
1684int QApplication::colorSpec()
1685{
1686 return QApplicationPrivate::app_cspec;
1687}
1688
1689/*!
1690 Sets the color specification for the application to \a spec.
1691
1692 The color specification controls how the application allocates colors when
1693 run on a display with a limited amount of colors, e.g. 8 bit / 256 color
1694 displays.
1695
1696 The color specification must be set before you create the QApplication
1697 object.
1698
1699 The options are:
1700 \list
1701 \o QApplication::NormalColor. This is the default color allocation
1702 strategy. Use this option if your application uses buttons, menus,
1703 texts and pixmaps with few colors. With this option, the
1704 application uses system global colors. This works fine for most
1705 applications under X11, but on the Windows platform, it may cause
1706 dithering of non-standard colors.
1707 \o QApplication::CustomColor. Use this option if your application
1708 needs a small number of custom colors. On X11, this option is the
1709 same as NormalColor. On Windows, Qt creates a Windows palette, and
1710 allocates colors to it on demand.
1711 \o QApplication::ManyColor. Use this option if your application is
1712 very color hungry, e.g., it requires thousands of colors. \br
1713 Under X11 the effect is:
1714 \list
1715 \o For 256-color displays which have at best a 256 color true
1716 color visual, the default visual is used, and colors are
1717 allocated from a color cube. The color cube is the 6x6x6
1718 (216 color) "Web palette" (the red, green, and blue
1719 components always have one of the following values: 0x00,
1720 0x33, 0x66, 0x99, 0xCC, or 0xFF), but the number of colors
1721 can be changed by the \e -ncols option. The user can force
1722 the application to use the true color visual with the
1723 \l{QApplication::QApplication()}{-visual} option.
1724 \o For 256-color displays which have a true color visual with
1725 more than 256 colors, use that visual. Silicon Graphics X
1726 servers this feature, for example. They provide an 8 bit
1727 visual by default but can deliver true color when asked.
1728 \endlist
1729 On Windows, Qt creates a Windows palette, and fills it with a color
1730 cube.
1731 \endlist
1732
1733 Be aware that the CustomColor and ManyColor choices may lead to colormap
1734 flashing: The foreground application gets (most) of the available colors,
1735 while the background windows will look less attractive.
1736
1737 Example:
1738
1739 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 2
1740
1741 \sa colorSpec()
1742*/
1743
1744void QApplication::setColorSpec(int spec)
1745{
1746 if (qApp)
1747 qWarning("QApplication::setColorSpec: This function must be "
1748 "called before the QApplication object is created");
1749 QApplicationPrivate::app_cspec = spec;
1750}
1751
1752/*!
1753 \property QApplication::globalStrut
1754 \brief the minimum size that any GUI element that the user can interact
1755 with should have
1756
1757 For example, no button should be resized to be smaller than the global
1758 strut size. The strut size should be considered when reimplementing GUI
1759 controls that may be used on touch-screens or similar I/O devices.
1760
1761 Example:
1762
1763 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 3
1764
1765 By default, this property contains a QSize object with zero width and height.
1766*/
1767QSize QApplication::globalStrut()
1768{
1769 return QApplicationPrivate::app_strut;
1770}
1771
1772void QApplication::setGlobalStrut(const QSize& strut)
1773{
1774 QApplicationPrivate::app_strut = strut;
1775}
1776
1777/*!
1778 Returns the application palette.
1779
1780 \sa setPalette(), QWidget::palette()
1781*/
1782QPalette QApplication::palette()
1783{
1784 if (!QApplicationPrivate::app_pal)
1785 QApplicationPrivate::app_pal = new QPalette(Qt::black);
1786 return *QApplicationPrivate::app_pal;
1787}
1788
1789/*!
1790 \fn QPalette QApplication::palette(const QWidget* widget)
1791 \overload
1792
1793 If a \a widget is passed, the default palette for the widget's class is
1794 returned. This may or may not be the application palette. In most cases
1795 there is no special palette for certain types of widgets, but one notable
1796 exception is the popup menu under Windows, if the user has defined a
1797 special background color for menus in the display settings.
1798
1799 \sa setPalette(), QWidget::palette()
1800*/
1801QPalette QApplication::palette(const QWidget* w)
1802{
1803 PaletteHash *hash = app_palettes();
1804 if (w && hash && hash->size()) {
1805 QHash<QByteArray, QPalette>::ConstIterator it = hash->constFind(w->metaObject()->className());
1806 if (it != hash->constEnd())
1807 return *it;
1808 for (it = hash->constBegin(); it != hash->constEnd(); ++it) {
1809 if (w->inherits(it.key()))
1810 return it.value();
1811 }
1812 }
1813 return palette();
1814}
1815
1816/*!
1817 \overload
1818
1819 Returns the palette for widgets of the given \a className.
1820
1821 \sa setPalette(), QWidget::palette()
1822*/
1823QPalette QApplication::palette(const char *className)
1824{
1825 if (!QApplicationPrivate::app_pal)
1826 palette();
1827 PaletteHash *hash = app_palettes();
1828 if (className && hash && hash->size()) {
1829 QHash<QByteArray, QPalette>::ConstIterator it = hash->constFind(className);
1830 if (it != hash->constEnd())
1831 return *it;
1832 }
1833 return *QApplicationPrivate::app_pal;
1834}
1835
1836void QApplicationPrivate::setPalette_helper(const QPalette &palette, const char* className, bool clearWidgetPaletteHash)
1837{
1838 QPalette pal = palette;
1839
1840 if (QApplicationPrivate::app_style)
1841 QApplicationPrivate::app_style->polish(pal); // NB: non-const reference
1842
1843 bool all = false;
1844 PaletteHash *hash = app_palettes();
1845 if (!className) {
1846 if (QApplicationPrivate::app_pal && pal.isCopyOf(*QApplicationPrivate::app_pal))
1847 return;
1848 if (!QApplicationPrivate::app_pal)
1849 QApplicationPrivate::app_pal = new QPalette(pal);
1850 else
1851 *QApplicationPrivate::app_pal = pal;
1852 if (hash && hash->size()) {
1853 all = true;
1854 if (clearWidgetPaletteHash)
1855 hash->clear();
1856 }
1857 } else if (hash) {
1858 hash->insert(className, pal);
1859 }
1860
1861 if (QApplicationPrivate::is_app_running && !QApplicationPrivate::is_app_closing) {
1862 // Send ApplicationPaletteChange to qApp itself, and to the widgets.
1863 QEvent e(QEvent::ApplicationPaletteChange);
1864 QApplication::sendEvent(QApplication::instance(), &e);
1865
1866 QWidgetList wids = QApplication::allWidgets();
1867 for (QWidgetList::ConstIterator it = wids.constBegin(); it != wids.constEnd(); ++it) {
1868 register QWidget *w = *it;
1869 if (all || (!className && w->isWindow()) || w->inherits(className)) // matching class
1870 QApplication::sendEvent(w, &e);
1871 }
1872
1873 // Send to all scenes as well.
1874#ifndef QT_NO_GRAPHICSVIEW
1875 QList<QGraphicsScene *> &scenes = qApp->d_func()->scene_list;
1876 for (QList<QGraphicsScene *>::ConstIterator it = scenes.constBegin();
1877 it != scenes.constEnd(); ++it) {
1878 QApplication::sendEvent(*it, &e);
1879 }
1880#endif //QT_NO_GRAPHICSVIEW
1881 }
1882 if (!className && (!QApplicationPrivate::sys_pal || !palette.isCopyOf(*QApplicationPrivate::sys_pal))) {
1883 if (!QApplicationPrivate::set_pal)
1884 QApplicationPrivate::set_pal = new QPalette(palette);
1885 else
1886 *QApplicationPrivate::set_pal = palette;
1887 }
1888}
1889
1890/*!
1891 Changes the default application palette to \a palette.
1892
1893 If \a className is passed, the change applies only to widgets that inherit
1894 \a className (as reported by QObject::inherits()). If \a className is left
1895 0, the change affects all widgets, thus overriding any previously set class
1896 specific palettes.
1897
1898 The palette may be changed according to the current GUI style in
1899 QStyle::polish().
1900
1901 \warning Do not use this function in conjunction with \l{Qt Style Sheets}.
1902 When using style sheets, the palette of a widget can be customized using
1903 the "color", "background-color", "selection-color",
1904 "selection-background-color" and "alternate-background-color".
1905
1906 \note Some styles do not use the palette for all drawing, for instance, if
1907 they make use of native theme engines. This is the case for the Windows XP,
1908 Windows Vista, and Mac OS X styles.
1909
1910 \sa QWidget::setPalette(), palette(), QStyle::polish()
1911*/
1912
1913void QApplication::setPalette(const QPalette &palette, const char* className)
1914{
1915 QApplicationPrivate::setPalette_helper(palette, className, /*clearWidgetPaletteHash=*/ true);
1916}
1917
1918
1919
1920void QApplicationPrivate::setSystemPalette(const QPalette &pal)
1921{
1922 QPalette adjusted;
1923
1924#if 0
1925 // adjust the system palette to avoid dithering
1926 QColormap cmap = QColormap::instance();
1927 if (cmap.depths() > 4 && cmap.depths() < 24) {
1928 for (int g = 0; g < QPalette::NColorGroups; g++)
1929 for (int i = 0; i < QPalette::NColorRoles; i++) {
1930 QColor color = pal.color((QPalette::ColorGroup)g, (QPalette::ColorRole)i);
1931 color = cmap.colorAt(cmap.pixel(color));
1932 adjusted.setColor((QPalette::ColorGroup)g, (QPalette::ColorRole) i, color);
1933 }
1934 }
1935#else
1936 adjusted = pal;
1937#endif
1938
1939 if (!sys_pal)
1940 sys_pal = new QPalette(adjusted);
1941 else
1942 *sys_pal = adjusted;
1943
1944
1945 if (!QApplicationPrivate::set_pal)
1946 QApplication::setPalette(*sys_pal);
1947}
1948
1949/*!
1950 Returns the default application font.
1951
1952 \sa fontMetrics(), QWidget::font()
1953*/
1954QFont QApplication::font()
1955{
1956 QMutexLocker locker(applicationFontMutex());
1957 if (!QApplicationPrivate::app_font) {
1958#if defined(Q_OS_BLACKBERRY)
1959 // See http://docs.blackberry.com/en/developers/deliverables/41577/typography.jsp
1960 // which recommends using font family "Slate Pro" and normal font size of 8 points
1961 QApplicationPrivate::app_font = new QFont(QLatin1String("Slate Pro"));
1962 QApplicationPrivate::app_font->setPointSize(8);
1963#else
1964 QApplicationPrivate::app_font = new QFont(QLatin1String("Helvetica"));
1965#endif
1966 }
1967 return *QApplicationPrivate::app_font;
1968}
1969
1970/*!
1971 \overload
1972
1973 Returns the default font for the \a widget.
1974
1975 \sa fontMetrics(), QWidget::setFont()
1976*/
1977
1978QFont QApplication::font(const QWidget *widget)
1979{
1980 FontHash *hash = app_fonts();
1981
1982#ifdef Q_WS_MAC
1983 // short circuit for small and mini controls
1984 if (widget->testAttribute(Qt::WA_MacSmallSize)) {
1985 return hash->value("QSmallFont");
1986 } else if (widget->testAttribute(Qt::WA_MacMiniSize)) {
1987 return hash->value("QMiniFont");
1988 }
1989#endif
1990 if (widget && hash && hash->size()) {
1991 QHash<QByteArray, QFont>::ConstIterator it =
1992 hash->constFind(widget->metaObject()->className());
1993 if (it != hash->constEnd())
1994 return it.value();
1995 for (it = hash->constBegin(); it != hash->constEnd(); ++it) {
1996 if (widget->inherits(it.key()))
1997 return it.value();
1998 }
1999 }
2000 return font();
2001}
2002
2003/*!
2004 \overload
2005
2006 Returns the font for widgets of the given \a className.
2007
2008 \sa setFont(), QWidget::font()
2009*/
2010QFont QApplication::font(const char *className)
2011{
2012 FontHash *hash = app_fonts();
2013 if (className && hash && hash->size()) {
2014 QHash<QByteArray, QFont>::ConstIterator it = hash->constFind(className);
2015 if (it != hash->constEnd())
2016 return *it;
2017 }
2018 return font();
2019}
2020
2021
2022/*!
2023 Changes the default application font to \a font. If \a className is passed,
2024 the change applies only to classes that inherit \a className (as reported
2025 by QObject::inherits()).
2026
2027 On application start-up, the default font depends on the window system. It
2028 can vary depending on both the window system version and the locale. This
2029 function lets you override the default font; but overriding may be a bad
2030 idea because, for example, some locales need extra large fonts to support
2031 their special characters.
2032
2033 \warning Do not use this function in conjunction with \l{Qt Style Sheets}.
2034 The font of an application can be customized using the "font" style sheet
2035 property. To set a bold font for all QPushButtons, set the application
2036 styleSheet() as "QPushButton { font: bold }"
2037
2038 \sa font(), fontMetrics(), QWidget::setFont()
2039*/
2040
2041void QApplication::setFont(const QFont &font, const char *className)
2042{
2043 bool all = false;
2044 FontHash *hash = app_fonts();
2045 if (!className) {
2046 QMutexLocker locker(applicationFontMutex());
2047 if (!QApplicationPrivate::app_font)
2048 QApplicationPrivate::app_font = new QFont(font);
2049 else
2050 *QApplicationPrivate::app_font = font;
2051 if (hash && hash->size()) {
2052 all = true;
2053 hash->clear();
2054 }
2055 } else if (hash) {
2056 hash->insert(className, font);
2057 }
2058 if (QApplicationPrivate::is_app_running && !QApplicationPrivate::is_app_closing) {
2059 // Send ApplicationFontChange to qApp itself, and to the widgets.
2060 QEvent e(QEvent::ApplicationFontChange);
2061 QApplication::sendEvent(QApplication::instance(), &e);
2062
2063 QWidgetList wids = QApplication::allWidgets();
2064 for (QWidgetList::ConstIterator it = wids.constBegin(); it != wids.constEnd(); ++it) {
2065 register QWidget *w = *it;
2066 if (all || (!className && w->isWindow()) || w->inherits(className)) // matching class
2067 sendEvent(w, &e);
2068 }
2069
2070#ifndef QT_NO_GRAPHICSVIEW
2071 // Send to all scenes as well.
2072 QList<QGraphicsScene *> &scenes = qApp->d_func()->scene_list;
2073 for (QList<QGraphicsScene *>::ConstIterator it = scenes.constBegin();
2074 it != scenes.constEnd(); ++it) {
2075 QApplication::sendEvent(*it, &e);
2076 }
2077#endif //QT_NO_GRAPHICSVIEW
2078 }
2079 if (!className && (!QApplicationPrivate::sys_font || !font.isCopyOf(*QApplicationPrivate::sys_font))) {
2080 if (!QApplicationPrivate::set_font)
2081 QApplicationPrivate::set_font = new QFont(font);
2082 else
2083 *QApplicationPrivate::set_font = font;
2084 }
2085}
2086
2087/*! \internal
2088*/
2089void QApplicationPrivate::setSystemFont(const QFont &font)
2090{
2091 if (!sys_font)
2092 sys_font = new QFont(font);
2093 else
2094 *sys_font = font;
2095
2096 if (!QApplicationPrivate::set_font)
2097 QApplication::setFont(*sys_font);
2098}
2099
2100/*! \internal
2101*/
2102QString QApplicationPrivate::desktopStyleKey()
2103{
2104 return qt_guiPlatformPlugin()->styleName();
2105}
2106
2107/*!
2108 \property QApplication::windowIcon
2109 \brief the default window icon
2110
2111 \sa QWidget::setWindowIcon(), {Setting the Application Icon}
2112*/
2113QIcon QApplication::windowIcon()
2114{
2115 return QApplicationPrivate::app_icon ? *QApplicationPrivate::app_icon : QIcon();
2116}
2117
2118void QApplication::setWindowIcon(const QIcon &icon)
2119{
2120 if (!QApplicationPrivate::app_icon)
2121 QApplicationPrivate::app_icon = new QIcon();
2122 *QApplicationPrivate::app_icon = icon;
2123 if (QApplicationPrivate::is_app_running && !QApplicationPrivate::is_app_closing) {
2124#ifdef Q_WS_MAC
2125 void qt_mac_set_app_icon(const QPixmap &); //qapplication_mac.cpp
2126 QSize size = QApplicationPrivate::app_icon->actualSize(QSize(128, 128));
2127 qt_mac_set_app_icon(QApplicationPrivate::app_icon->pixmap(size));
2128#endif
2129 QEvent e(QEvent::ApplicationWindowIconChange);
2130 QWidgetList all = QApplication::allWidgets();
2131 for (QWidgetList::ConstIterator it = all.constBegin(); it != all.constEnd(); ++it) {
2132 register QWidget *w = *it;
2133 if (w->isWindow())
2134 sendEvent(w, &e);
2135 }
2136 }
2137}
2138
2139/*!
2140 Returns a list of the top-level widgets (windows) in the application.
2141
2142 \note Some of the top-level widgets may be hidden, for example a tooltip if
2143 no tooltip is currently shown.
2144
2145 Example:
2146
2147 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 4
2148
2149 \sa allWidgets(), QWidget::isWindow(), QWidget::isHidden()
2150*/
2151QWidgetList QApplication::topLevelWidgets()
2152{
2153 QWidgetList list;
2154 QWidgetList all = allWidgets();
2155
2156 for (QWidgetList::ConstIterator it = all.constBegin(); it != all.constEnd(); ++it) {
2157 QWidget *w = *it;
2158 if (w->isWindow() && w->windowType() != Qt::Desktop)
2159 list.append(w);
2160 }
2161 return list;
2162}
2163
2164/*!
2165 Returns a list of all the widgets in the application.
2166
2167 The list is empty (QList::isEmpty()) if there are no widgets.
2168
2169 \note Some of the widgets may be hidden.
2170
2171 Example:
2172 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 5
2173
2174 \sa topLevelWidgets(), QWidget::isVisible()
2175*/
2176
2177QWidgetList QApplication::allWidgets()
2178{
2179 if (QWidgetPrivate::allWidgets)
2180 return QWidgetPrivate::allWidgets->toList();
2181 return QWidgetList();
2182}
2183
2184/*!
2185 Returns the application widget that has the keyboard input focus, or 0 if
2186 no widget in this application has the focus.
2187
2188 \sa QWidget::setFocus(), QWidget::hasFocus(), activeWindow(), focusChanged()
2189*/
2190
2191QWidget *QApplication::focusWidget()
2192{
2193 return QApplicationPrivate::focus_widget;
2194}
2195
2196void QApplicationPrivate::setFocusWidget(QWidget *focus, Qt::FocusReason reason)
2197{
2198#ifndef QT_NO_GRAPHICSVIEW
2199 if (focus && focus->window()->graphicsProxyWidget())
2200 return;
2201#endif
2202
2203 hidden_focus_widget = 0;
2204
2205 if (focus != focus_widget) {
2206 if (focus && focus->isHidden()) {
2207 hidden_focus_widget = focus;
2208 return;
2209 }
2210
2211 if (focus && (reason == Qt::BacktabFocusReason || reason == Qt::TabFocusReason)
2212 && qt_in_tab_key_event)
2213 focus->window()->setAttribute(Qt::WA_KeyboardFocusChange);
2214 else if (focus && reason == Qt::ShortcutFocusReason) {
2215 focus->window()->setAttribute(Qt::WA_KeyboardFocusChange);
2216 }
2217 QWidget *prev = focus_widget;
2218 focus_widget = focus;
2219#ifndef QT_NO_IM
2220 if (prev && ((reason != Qt::PopupFocusReason && reason != Qt::MenuBarFocusReason
2221 && prev->testAttribute(Qt::WA_InputMethodEnabled))
2222 // Do reset the input context, in case the new focus widget won't accept keyboard input
2223 // or it is not created fully yet.
2224 || (focus_widget && (!focus_widget->testAttribute(Qt::WA_InputMethodEnabled)
2225 || !focus_widget->testAttribute(Qt::WA_WState_Created))))) {
2226 QInputContext *qic = prev->inputContext();
2227 if(qic) {
2228 qic->reset();
2229 qic->setFocusWidget(0);
2230 }
2231 }
2232#endif //QT_NO_IM
2233
2234 if(focus_widget)
2235 focus_widget->d_func()->setFocus_sys();
2236
2237 if (reason != Qt::NoFocusReason) {
2238
2239 //send events
2240 if (prev) {
2241#ifdef QT_KEYPAD_NAVIGATION
2242 if (QApplication::keypadNavigationEnabled()) {
2243 if (prev->hasEditFocus() && reason != Qt::PopupFocusReason
2244#ifdef Q_OS_SYMBIAN
2245 && reason != Qt::ActiveWindowFocusReason
2246#endif
2247 )
2248 prev->setEditFocus(false);
2249 }
2250#endif
2251#ifndef QT_NO_IM
2252 if (focus) {
2253 QInputContext *prevIc;
2254 prevIc = prev->inputContext();
2255 if (prevIc && prevIc != focus->inputContext()) {
2256 QEvent closeSIPEvent(QEvent::CloseSoftwareInputPanel);
2257 QApplication::sendEvent(prev, &closeSIPEvent);
2258 }
2259 }
2260#endif
2261 QFocusEvent out(QEvent::FocusOut, reason);
2262 QPointer<QWidget> that = prev;
2263 QApplication::sendEvent(prev, &out);
2264 if (that)
2265 QApplication::sendEvent(that->style(), &out);
2266 }
2267 if(focus && QApplicationPrivate::focus_widget == focus) {
2268#ifndef QT_NO_IM
2269 if (focus->testAttribute(Qt::WA_InputMethodEnabled)) {
2270 QInputContext *qic = focus->inputContext();
2271 if (qic && focus->testAttribute(Qt::WA_WState_Created)
2272 && focus->isEnabled())
2273 qic->setFocusWidget(focus);
2274 }
2275#endif //QT_NO_IM
2276 QFocusEvent in(QEvent::FocusIn, reason);
2277 QPointer<QWidget> that = focus;
2278 QApplication::sendEvent(focus, &in);
2279 if (that)
2280 QApplication::sendEvent(that->style(), &in);
2281 }
2282 emit qApp->focusChanged(prev, focus_widget);
2283 }
2284 }
2285}
2286
2287
2288/*!
2289 Returns the application top-level window that has the keyboard input focus,
2290 or 0 if no application window has the focus. There might be an
2291 activeWindow() even if there is no focusWidget(), for example if no widget
2292 in that window accepts key events.
2293
2294 \sa QWidget::setFocus(), QWidget::hasFocus(), focusWidget()
2295*/
2296
2297QWidget *QApplication::activeWindow()
2298{
2299 return QApplicationPrivate::active_window;
2300}
2301
2302/*!
2303 Returns display (screen) font metrics for the application font.
2304
2305 \sa font(), setFont(), QWidget::fontMetrics(), QPainter::fontMetrics()
2306*/
2307
2308QFontMetrics QApplication::fontMetrics()
2309{
2310 return desktop()->fontMetrics();
2311}
2312
2313
2314/*!
2315 Closes all top-level windows.
2316
2317 This function is particularly useful for applications with many top-level
2318 windows. It could, for example, be connected to a \gui{Exit} entry in the
2319 \gui{File} menu:
2320
2321 \snippet examples/mainwindows/mdi/mainwindow.cpp 0
2322
2323 The windows are closed in random order, until one window does not accept
2324 the close event. The application quits when the last window was
2325 successfully closed; this can be turned off by setting
2326 \l quitOnLastWindowClosed to false.
2327
2328 \sa quitOnLastWindowClosed, lastWindowClosed(), QWidget::close(),
2329 QWidget::closeEvent(), lastWindowClosed(), quit(), topLevelWidgets(),
2330 QWidget::isWindow()
2331*/
2332void QApplication::closeAllWindows()
2333{
2334 bool did_close = true;
2335 QWidget *w;
2336 while ((w = activeModalWidget()) && did_close) {
2337 if (!w->isVisible() || w->data->is_closing)
2338 break;
2339 did_close = w->close();
2340 }
2341 QWidgetList list = QApplication::topLevelWidgets();
2342 for (int i = 0; did_close && i < list.size(); ++i) {
2343 w = list.at(i);
2344 if (w->isVisible()
2345 && w->windowType() != Qt::Desktop
2346 && !w->data->is_closing) {
2347 did_close = w->close();
2348 list = QApplication::topLevelWidgets();
2349 i = -1;
2350 }
2351 }
2352}
2353
2354/*!
2355 Displays a simple message box about Qt. The message includes the version
2356 number of Qt being used by the application.
2357
2358 This is useful for inclusion in the \gui Help menu of an application, as
2359 shown in the \l{mainwindows/menus}{Menus} example.
2360
2361 This function is a convenience slot for QMessageBox::aboutQt().
2362*/
2363void QApplication::aboutQt()
2364{
2365#ifndef QT_NO_MESSAGEBOX
2366 QMessageBox::aboutQt(
2367#ifdef Q_WS_MAC
2368 0
2369#else
2370 activeWindow()
2371#endif // Q_WS_MAC
2372 );
2373#endif // QT_NO_MESSAGEBOX
2374}
2375
2376
2377/*!
2378 \fn void QApplication::lastWindowClosed()
2379
2380 This signal is emitted from QApplication::exec() when the last visible
2381 primary window (i.e. window with no parent) with the Qt::WA_QuitOnClose
2382 attribute set is closed.
2383
2384 By default,
2385
2386 \list
2387 \o this attribute is set for all widgets except transient windows such
2388 as splash screens, tool windows, and popup menus
2389
2390 \o QApplication implicitly quits when this signal is emitted.
2391 \endlist
2392
2393 This feature can be turned off by setting \l quitOnLastWindowClosed to
2394 false.
2395
2396 \sa QWidget::close()
2397*/
2398
2399/*!
2400 \since 4.1
2401 \fn void QApplication::focusChanged(QWidget *old, QWidget *now)
2402
2403 This signal is emitted when the widget that has keyboard focus changed from
2404 \a old to \a now, i.e., because the user pressed the tab-key, clicked into
2405 a widget or changed the active window. Both \a old and \a now can be the
2406 null-pointer.
2407
2408 The signal is emitted after both widget have been notified about the change
2409 through QFocusEvent.
2410
2411 \sa QWidget::setFocus(), QWidget::clearFocus(), Qt::FocusReason
2412*/
2413
2414/*!
2415 \since 4.5
2416 \fn void QApplication::fontDatabaseChanged()
2417
2418 This signal is emitted when application fonts are loaded or removed.
2419
2420 \sa QFontDatabase::addApplicationFont(),
2421 QFontDatabase::addApplicationFontFromData(),
2422 QFontDatabase::removeAllApplicationFonts(),
2423 QFontDatabase::removeApplicationFont()
2424*/
2425
2426#ifndef QT_NO_TRANSLATION
2427static bool qt_detectRTLLanguage()
2428{
2429 return force_reverse ^
2430 (QApplication::tr("QT_LAYOUT_DIRECTION",
2431 "Translate this string to the string 'LTR' in left-to-right"
2432 " languages or to 'RTL' in right-to-left languages (such as Hebrew"
2433 " and Arabic) to get proper widget layout.") == QLatin1String("RTL"));
2434}
2435#if defined(Q_WS_MAC)
2436static const char *application_menu_strings[] = {
2437 QT_TRANSLATE_NOOP("MAC_APPLICATION_MENU","Services"),
2438 QT_TRANSLATE_NOOP("MAC_APPLICATION_MENU","Hide %1"),
2439 QT_TRANSLATE_NOOP("MAC_APPLICATION_MENU","Hide Others"),
2440 QT_TRANSLATE_NOOP("MAC_APPLICATION_MENU","Show All"),
2441 QT_TRANSLATE_NOOP("MAC_APPLICATION_MENU","Preferences..."),
2442 QT_TRANSLATE_NOOP("MAC_APPLICATION_MENU","Quit %1"),
2443 QT_TRANSLATE_NOOP("MAC_APPLICATION_MENU","About %1")
2444 };
2445QString qt_mac_applicationmenu_string(int type)
2446{
2447 QString menuString = QString::fromLatin1(application_menu_strings[type]);
2448 QString translated = qApp->translate("QMenuBar", application_menu_strings[type]);
2449 if (translated != menuString)
2450 return translated;
2451 else
2452 return qApp->translate("MAC_APPLICATION_MENU",
2453 application_menu_strings[type]);
2454}
2455#endif
2456#endif
2457
2458/*!\reimp
2459
2460*/
2461bool QApplication::event(QEvent *e)
2462{
2463 Q_D(QApplication);
2464 if(e->type() == QEvent::Close) {
2465#if defined(Q_OS_SYMBIAN)
2466 // In order to have proper application-exit effects on Symbian, certain
2467 // native APIs have to be called _before_ closing/destroying the widgets.
2468 bool effectStarted = qt_beginFullScreenEffect();
2469#endif
2470 QCloseEvent *ce = static_cast<QCloseEvent*>(e);
2471 ce->accept();
2472 closeAllWindows();
2473
2474 QWidgetList list = topLevelWidgets();
2475 for (int i = 0; i < list.size(); ++i) {
2476 QWidget *w = list.at(i);
2477 if (w->isVisible() && !(w->windowType() == Qt::Desktop) && !(w->windowType() == Qt::Popup) &&
2478 (!(w->windowType() == Qt::Dialog) || !w->parentWidget())) {
2479 ce->ignore();
2480 break;
2481 }
2482 }
2483 if (ce->isAccepted()) {
2484 return true;
2485 } else {
2486#if defined(Q_OS_SYMBIAN)
2487 if (effectStarted)
2488 qt_abortFullScreenEffect();
2489#endif
2490 }
2491 } else if(e->type() == QEvent::LanguageChange) {
2492#ifndef QT_NO_TRANSLATION
2493 setLayoutDirection(qt_detectRTLLanguage()?Qt::RightToLeft:Qt::LeftToRight);
2494#endif
2495#if defined(QT_MAC_USE_COCOA)
2496 qt_mac_post_retranslateAppMenu();
2497#endif
2498 QWidgetList list = topLevelWidgets();
2499 for (int i = 0; i < list.size(); ++i) {
2500 QWidget *w = list.at(i);
2501 if (!(w->windowType() == Qt::Desktop))
2502 postEvent(w, new QEvent(QEvent::LanguageChange));
2503 }
2504#ifndef Q_OS_WIN
2505 } else if (e->type() == QEvent::LocaleChange) {
2506 // on Windows the event propagation is taken care by the
2507 // WM_SETTINGCHANGE event handler.
2508 QWidgetList list = topLevelWidgets();
2509 for (int i = 0; i < list.size(); ++i) {
2510 QWidget *w = list.at(i);
2511 if (!(w->windowType() == Qt::Desktop)) {
2512 if (!w->testAttribute(Qt::WA_SetLocale))
2513 w->d_func()->setLocale_helper(QLocale(), true);
2514 }
2515 }
2516#endif
2517 } else if (e->type() == QEvent::Timer) {
2518 QTimerEvent *te = static_cast<QTimerEvent*>(e);
2519 Q_ASSERT(te != 0);
2520 if (te->timerId() == d->toolTipWakeUp.timerId()) {
2521 d->toolTipWakeUp.stop();
2522 if (d->toolTipWidget) {
2523 QWidget *w = d->toolTipWidget->window();
2524 // show tooltip if WA_AlwaysShowToolTips is set, or if
2525 // any ancestor of d->toolTipWidget is the active
2526 // window
2527 bool showToolTip = w->testAttribute(Qt::WA_AlwaysShowToolTips);
2528 while (w && !showToolTip) {
2529 showToolTip = w->isActiveWindow();
2530 w = w->parentWidget();
2531 w = w ? w->window() : 0;
2532 }
2533 if (showToolTip) {
2534 QHelpEvent e(QEvent::ToolTip, d->toolTipPos, d->toolTipGlobalPos);
2535 QApplication::sendEvent(d->toolTipWidget, &e);
2536 if (e.isAccepted())
2537 d->toolTipFallAsleep.start(2000, this);
2538 }
2539 }
2540 } else if (te->timerId() == d->toolTipFallAsleep.timerId()) {
2541 d->toolTipFallAsleep.stop();
2542 }
2543 }
2544 return QCoreApplication::event(e);
2545}
2546#if !defined(Q_WS_X11)
2547
2548// The doc and X implementation of this function is in qapplication_x11.cpp
2549
2550void QApplication::syncX() {} // do nothing
2551
2552#endif
2553
2554/*!
2555 \fn Qt::WindowsVersion QApplication::winVersion()
2556
2557 Use \l QSysInfo::WindowsVersion instead.
2558*/
2559
2560/*!
2561 \fn void QApplication::setActiveWindow(QWidget* active)
2562
2563 Sets the active window to the \a active widget in response to a system
2564 event. The function is called from the platform specific event handlers.
2565
2566 \warning This function does \e not set the keyboard focus to the active
2567 widget. Call QWidget::activateWindow() instead.
2568
2569 It sets the activeWindow() and focusWidget() attributes and sends proper
2570 \l{QEvent::WindowActivate}{WindowActivate}/\l{QEvent::WindowDeactivate}
2571 {WindowDeactivate} and \l{QEvent::FocusIn}{FocusIn}/\l{QEvent::FocusOut}
2572 {FocusOut} events to all appropriate widgets. The window will then be
2573 painted in active state (e.g. cursors in line edits will blink), and it
2574 will have tool tips enabled.
2575
2576 \sa activeWindow(), QWidget::activateWindow()
2577*/
2578void QApplication::setActiveWindow(QWidget* act)
2579{
2580 QWidget* window = act?act->window():0;
2581
2582 if (QApplicationPrivate::active_window == window)
2583 return;
2584
2585#ifndef QT_NO_GRAPHICSVIEW
2586 if (window && window->graphicsProxyWidget()) {
2587 // Activate the proxy's view->viewport() ?
2588 return;
2589 }
2590#endif
2591
2592 QWidgetList toBeActivated;
2593 QWidgetList toBeDeactivated;
2594
2595 if (QApplicationPrivate::active_window) {
2596 if (style()->styleHint(QStyle::SH_Widget_ShareActivation, 0, QApplicationPrivate::active_window)) {
2597 QWidgetList list = topLevelWidgets();
2598 for (int i = 0; i < list.size(); ++i) {
2599 QWidget *w = list.at(i);
2600 if (w->isVisible() && w->isActiveWindow())
2601 toBeDeactivated.append(w);
2602 }
2603 } else {
2604 toBeDeactivated.append(QApplicationPrivate::active_window);
2605 }
2606 }
2607
2608#if !defined(Q_WS_MAC)
2609 QWidget *previousActiveWindow = QApplicationPrivate::active_window;
2610#endif
2611 QApplicationPrivate::active_window = window;
2612
2613 if (QApplicationPrivate::active_window) {
2614 if (style()->styleHint(QStyle::SH_Widget_ShareActivation, 0, QApplicationPrivate::active_window)) {
2615 QWidgetList list = topLevelWidgets();
2616 for (int i = 0; i < list.size(); ++i) {
2617 QWidget *w = list.at(i);
2618 if (w->isVisible() && w->isActiveWindow())
2619 toBeActivated.append(w);
2620 }
2621 } else {
2622 toBeActivated.append(QApplicationPrivate::active_window);
2623 }
2624
2625 }
2626
2627 // first the activation/deactivation events
2628 QEvent activationChange(QEvent::ActivationChange);
2629 QEvent windowActivate(QEvent::WindowActivate);
2630 QEvent windowDeactivate(QEvent::WindowDeactivate);
2631
2632#if !defined(Q_WS_MAC)
2633 if (!previousActiveWindow) {
2634 QEvent appActivate(QEvent::ApplicationActivate);
2635 sendSpontaneousEvent(qApp, &appActivate);
2636 }
2637#endif
2638
2639 for (int i = 0; i < toBeActivated.size(); ++i) {
2640 QWidget *w = toBeActivated.at(i);
2641 sendSpontaneousEvent(w, &windowActivate);
2642 sendSpontaneousEvent(w, &activationChange);
2643 }
2644
2645#ifdef QT_MAC_USE_COCOA
2646 // In case the user clicked on a child window, we need to
2647 // reestablish the stacking order of the window so
2648 // it pops in front of other child windows in cocoa:
2649 qt_cocoaStackChildWindowOnTopOfOtherChildren(window);
2650#endif
2651
2652 for(int i = 0; i < toBeDeactivated.size(); ++i) {
2653 QWidget *w = toBeDeactivated.at(i);
2654 sendSpontaneousEvent(w, &windowDeactivate);
2655 sendSpontaneousEvent(w, &activationChange);
2656 }
2657
2658#if !defined(Q_WS_MAC)
2659 if (!QApplicationPrivate::active_window) {
2660 QEvent appDeactivate(QEvent::ApplicationDeactivate);
2661 sendSpontaneousEvent(qApp, &appDeactivate);
2662 }
2663#endif
2664
2665 if (QApplicationPrivate::popupWidgets == 0) { // !inPopupMode()
2666 // then focus events
2667 if (!QApplicationPrivate::active_window && QApplicationPrivate::focus_widget) {
2668 QApplicationPrivate::setFocusWidget(0, Qt::ActiveWindowFocusReason);
2669 } else if (QApplicationPrivate::active_window) {
2670 QWidget *w = QApplicationPrivate::active_window->focusWidget();
2671 if (w && w->isVisible() /*&& w->focusPolicy() != QWidget::NoFocus*/)
2672 w->setFocus(Qt::ActiveWindowFocusReason);
2673 else {
2674 w = QApplicationPrivate::focusNextPrevChild_helper(QApplicationPrivate::active_window, true);
2675 if (w) {
2676 w->setFocus(Qt::ActiveWindowFocusReason);
2677 } else {
2678 // If the focus widget is not in the activate_window, clear the focus
2679 w = QApplicationPrivate::focus_widget;
2680 if (!w && QApplicationPrivate::active_window->focusPolicy() != Qt::NoFocus)
2681 QApplicationPrivate::setFocusWidget(QApplicationPrivate::active_window, Qt::ActiveWindowFocusReason);
2682 else if (!QApplicationPrivate::active_window->isAncestorOf(w))
2683 QApplicationPrivate::setFocusWidget(0, Qt::ActiveWindowFocusReason);
2684 }
2685 }
2686 }
2687 }
2688}
2689
2690/*!internal
2691 * Helper function that returns the new focus widget, but does not set the focus reason.
2692 * Returns 0 if a new focus widget could not be found.
2693 * Shared with QGraphicsProxyWidgetPrivate::findFocusChild()
2694*/
2695QWidget *QApplicationPrivate::focusNextPrevChild_helper(QWidget *toplevel, bool next)
2696{
2697 uint focus_flag = qt_tab_all_widgets ? Qt::TabFocus : Qt::StrongFocus;
2698
2699 QWidget *f = toplevel->focusWidget();
2700 if (!f)
2701 f = toplevel;
2702
2703 QWidget *w = f;
2704 QWidget *test = f->d_func()->focus_next;
2705 while (test && test != f) {
2706 if ((test->focusPolicy() & focus_flag) == focus_flag
2707 && !(test->d_func()->extra && test->d_func()->extra->focus_proxy)
2708 && test->isVisibleTo(toplevel) && test->isEnabled()
2709 && !(w->windowType() == Qt::SubWindow && !w->isAncestorOf(test))
2710 && (toplevel->windowType() != Qt::SubWindow || toplevel->isAncestorOf(test))) {
2711 w = test;
2712 if (next)
2713 break;
2714 }
2715 test = test->d_func()->focus_next;
2716 }
2717 if (w == f) {
2718 if (qt_in_tab_key_event) {
2719 w->window()->setAttribute(Qt::WA_KeyboardFocusChange);
2720 w->update();
2721 }
2722 return 0;
2723 }
2724 return w;
2725}
2726
2727/*!
2728 \fn void QApplicationPrivate::dispatchEnterLeave(QWidget* enter, QWidget* leave)
2729 \internal
2730
2731 Creates the proper Enter/Leave event when widget \a enter is entered and
2732 widget \a leave is left.
2733 */
2734void QApplicationPrivate::dispatchEnterLeave(QWidget* enter, QWidget* leave) {
2735#if 0
2736 if (leave) {
2737 QEvent e(QEvent::Leave);
2738 QApplication::sendEvent(leave, & e);
2739 }
2740 if (enter) {
2741 QEvent e(QEvent::Enter);
2742 QApplication::sendEvent(enter, & e);
2743 }
2744 return;
2745#endif
2746
2747 QWidget* w ;
2748 if ((!enter && !leave) || (enter == leave))
2749 return;
2750#ifdef ALIEN_DEBUG
2751 qDebug() << "QApplicationPrivate::dispatchEnterLeave, ENTER:" << enter << "LEAVE:" << leave;
2752#endif
2753 QWidgetList leaveList;
2754 QWidgetList enterList;
2755
2756 bool sameWindow = leave && enter && leave->window() == enter->window();
2757 if (leave && !sameWindow) {
2758 w = leave;
2759 do {
2760 leaveList.append(w);
2761 } while (!w->isWindow() && (w = w->parentWidget()));
2762 }
2763 if (enter && !sameWindow) {
2764 w = enter;
2765 do {
2766 enterList.prepend(w);
2767 } while (!w->isWindow() && (w = w->parentWidget()));
2768 }
2769 if (sameWindow) {
2770 int enterDepth = 0;
2771 int leaveDepth = 0;
2772 w = enter;
2773 while (!w->isWindow() && (w = w->parentWidget()))
2774 enterDepth++;
2775 w = leave;
2776 while (!w->isWindow() && (w = w->parentWidget()))
2777 leaveDepth++;
2778 QWidget* wenter = enter;
2779 QWidget* wleave = leave;
2780 while (enterDepth > leaveDepth) {
2781 wenter = wenter->parentWidget();
2782 enterDepth--;
2783 }
2784 while (leaveDepth > enterDepth) {
2785 wleave = wleave->parentWidget();
2786 leaveDepth--;
2787 }
2788 while (!wenter->isWindow() && wenter != wleave) {
2789 wenter = wenter->parentWidget();
2790 wleave = wleave->parentWidget();
2791 }
2792
2793 w = leave;
2794 while (w != wleave) {
2795 leaveList.append(w);
2796 w = w->parentWidget();
2797 }
2798 w = enter;
2799 while (w != wenter) {
2800 enterList.prepend(w);
2801 w = w->parentWidget();
2802 }
2803 }
2804
2805 QEvent leaveEvent(QEvent::Leave);
2806 for (int i = 0; i < leaveList.size(); ++i) {
2807 w = leaveList.at(i);
2808 if (!QApplication::activeModalWidget() || QApplicationPrivate::tryModalHelper(w, 0)) {
2809#if defined(Q_WS_WIN) || defined(Q_WS_X11) || defined(Q_WS_MAC)
2810 if (leaveAfterRelease == w)
2811 leaveAfterRelease = 0;
2812#endif
2813 QApplication::sendEvent(w, &leaveEvent);
2814 if (w->testAttribute(Qt::WA_Hover) &&
2815 (!QApplication::activePopupWidget() || QApplication::activePopupWidget() == w->window())) {
2816 Q_ASSERT(instance());
2817 QHoverEvent he(QEvent::HoverLeave, QPoint(-1, -1), w->mapFromGlobal(QApplicationPrivate::instance()->hoverGlobalPos));
2818 qApp->d_func()->notify_helper(w, &he);
2819 }
2820 }
2821 }
2822 QPoint posEnter = QCursor::pos();
2823 QEvent enterEvent(QEvent::Enter);
2824 for (int i = 0; i < enterList.size(); ++i) {
2825 w = enterList.at(i);
2826 if (!QApplication::activeModalWidget() || QApplicationPrivate::tryModalHelper(w, 0)) {
2827 QApplication::sendEvent(w, &enterEvent);
2828 if (w->testAttribute(Qt::WA_Hover) &&
2829 (!QApplication::activePopupWidget() || QApplication::activePopupWidget() == w->window())) {
2830 QHoverEvent he(QEvent::HoverEnter, w->mapFromGlobal(posEnter), QPoint(-1, -1));
2831 qApp->d_func()->notify_helper(w, &he);
2832 }
2833 }
2834 }
2835
2836#ifndef QT_NO_CURSOR
2837 // Update cursor for alien/graphics widgets.
2838
2839 const bool enterOnAlien = (enter && (isAlien(enter) || enter->testAttribute(Qt::WA_DontShowOnScreen)));
2840#if defined(Q_WS_X11) || defined(Q_WS_QPA)
2841 //Whenever we leave an alien widget on X11, we need to reset its nativeParentWidget()'s cursor.
2842 // This is not required on Windows as the cursor is reset on every single mouse move.
2843 QWidget *parentOfLeavingCursor = 0;
2844 for (int i = 0; i < leaveList.size(); ++i) {
2845 w = leaveList.at(i);
2846 if (!isAlien(w))
2847 break;
2848 if (w->testAttribute(Qt::WA_SetCursor)) {
2849 QWidget *parent = w->parentWidget();
2850 while (parent && parent->d_func()->data.in_destructor)
2851 parent = parent->parentWidget();
2852 parentOfLeavingCursor = parent;
2853 //continue looping, we need to find the downest alien widget with a cursor.
2854 // (downest on the screen)
2855 }
2856 }
2857 //check that we will not call qt_x11_enforce_cursor twice with the same native widget
2858 if (parentOfLeavingCursor && (!enterOnAlien
2859 || parentOfLeavingCursor->effectiveWinId() != enter->effectiveWinId())) {
2860#ifndef QT_NO_GRAPHICSVIEW
2861 if (!parentOfLeavingCursor->window()->graphicsProxyWidget())
2862#endif
2863 {
2864#if defined(Q_WS_X11)
2865 qt_x11_enforce_cursor(parentOfLeavingCursor,true);
2866#elif defined(Q_WS_QPA)
2867 if (enter == QApplication::desktop()) {
2868 qt_qpa_set_cursor(enter, true);
2869 } else {
2870 qt_qpa_set_cursor(parentOfLeavingCursor, true);
2871 }
2872#endif
2873 }
2874 }
2875#endif
2876 if (enterOnAlien) {
2877 QWidget *cursorWidget = enter;
2878 while (!cursorWidget->isWindow() && !cursorWidget->isEnabled())
2879 cursorWidget = cursorWidget->parentWidget();
2880
2881 if (!cursorWidget)
2882 return;
2883
2884#ifndef QT_NO_GRAPHICSVIEW
2885 if (cursorWidget->window()->graphicsProxyWidget()) {
2886 QWidgetPrivate::nearestGraphicsProxyWidget(cursorWidget)->setCursor(cursorWidget->cursor());
2887 } else
2888#endif
2889 {
2890#if defined(Q_WS_WIN)
2891 qt_win_set_cursor(cursorWidget, true);
2892#elif defined(Q_WS_X11)
2893 qt_x11_enforce_cursor(cursorWidget, true);
2894#elif defined(Q_OS_SYMBIAN)
2895 qt_symbian_set_cursor(cursorWidget, true);
2896#elif defined(Q_WS_QPA)
2897 qt_qpa_set_cursor(cursorWidget, true);
2898#endif
2899 }
2900 }
2901#endif
2902}
2903
2904/* exported for the benefit of testing tools */
2905Q_GUI_EXPORT bool qt_tryModalHelper(QWidget *widget, QWidget **rettop)
2906{
2907 return QApplicationPrivate::tryModalHelper(widget, rettop);
2908}
2909
2910/*! \internal
2911 Returns true if \a widget is blocked by a modal window.
2912 */
2913bool QApplicationPrivate::isBlockedByModal(QWidget *widget)
2914{
2915 widget = widget->window();
2916 if (!modalState())
2917 return false;
2918 if (QApplication::activePopupWidget() == widget)
2919 return false;
2920
2921 for (int i = 0; i < qt_modal_stack->size(); ++i) {
2922 QWidget *modalWidget = qt_modal_stack->at(i);
2923
2924 {
2925 // check if the active modal widget is our widget or a parent of our widget
2926 QWidget *w = widget;
2927 while (w) {
2928 if (w == modalWidget)
2929 return false;
2930 w = w->parentWidget();
2931 }
2932#ifdef Q_WS_WIN
2933 if ((widget->testAttribute(Qt::WA_WState_Created) || widget->data->winid)
2934 && (modalWidget->testAttribute(Qt::WA_WState_Created) || modalWidget->data->winid)
2935 && IsChild(modalWidget->data->winid, widget->data->winid))
2936 return false;
2937#endif
2938 }
2939
2940 Qt::WindowModality windowModality = modalWidget->windowModality();
2941 if (windowModality == Qt::NonModal) {
2942 // determine the modality type if it hasn't been set on the
2943 // modalWidget, this normally happens when waiting for a
2944 // native dialog. use WindowModal if we are the child of a
2945 // group leader; otherwise use ApplicationModal.
2946 QWidget *m = modalWidget;
2947 while (m && !m->testAttribute(Qt::WA_GroupLeader)) {
2948 m = m->parentWidget();
2949 if (m)
2950 m = m->window();
2951 }
2952 windowModality = (m && m->testAttribute(Qt::WA_GroupLeader))
2953 ? Qt::WindowModal
2954 : Qt::ApplicationModal;
2955 }
2956
2957 switch (windowModality) {
2958 case Qt::ApplicationModal:
2959 {
2960 QWidget *groupLeaderForWidget = widget;
2961 while (groupLeaderForWidget && !groupLeaderForWidget->testAttribute(Qt::WA_GroupLeader))
2962 groupLeaderForWidget = groupLeaderForWidget->parentWidget();
2963
2964 if (groupLeaderForWidget) {
2965 // if \a widget has WA_GroupLeader, it can only be blocked by ApplicationModal children
2966 QWidget *m = modalWidget;
2967 while (m && m != groupLeaderForWidget && !m->testAttribute(Qt::WA_GroupLeader))
2968 m = m->parentWidget();
2969 if (m == groupLeaderForWidget)
2970 return true;
2971 } else if (modalWidget != widget) {
2972 return true;
2973 }
2974 break;
2975 }
2976 case Qt::WindowModal:
2977 {
2978 QWidget *w = widget;
2979 do {
2980 QWidget *m = modalWidget;
2981 do {
2982 if (m == w)
2983 return true;
2984 m = m->parentWidget();
2985 if (m)
2986 m = m->window();
2987 } while (m);
2988 w = w->parentWidget();
2989 if (w)
2990 w = w->window();
2991 } while (w);
2992 break;
2993 }
2994 default:
2995 Q_ASSERT_X(false, "QApplication", "internal error, a modal widget cannot be modeless");
2996 break;
2997 }
2998 }
2999 return false;
3000}
3001
3002/*!\internal
3003 */
3004void QApplicationPrivate::enterModal(QWidget *widget)
3005{
3006 QSet<QWidget*> blocked;
3007 QList<QWidget*> windows = QApplication::topLevelWidgets();
3008 for (int i = 0; i < windows.count(); ++i) {
3009 QWidget *window = windows.at(i);
3010 if (window->windowType() != Qt::Tool && isBlockedByModal(window))
3011 blocked.insert(window);
3012 }
3013
3014 enterModal_sys(widget);
3015
3016 windows = QApplication::topLevelWidgets();
3017 QEvent e(QEvent::WindowBlocked);
3018 for (int i = 0; i < windows.count(); ++i) {
3019 QWidget *window = windows.at(i);
3020 if (!blocked.contains(window) && window->windowType() != Qt::Tool && isBlockedByModal(window))
3021 QApplication::sendEvent(window, &e);
3022 }
3023}
3024
3025/*!\internal
3026 */
3027void QApplicationPrivate::leaveModal(QWidget *widget)
3028{
3029 QSet<QWidget*> blocked;
3030 QList<QWidget*> windows = QApplication::topLevelWidgets();
3031 for (int i = 0; i < windows.count(); ++i) {
3032 QWidget *window = windows.at(i);
3033 if (window->windowType() != Qt::Tool && isBlockedByModal(window))
3034 blocked.insert(window);
3035 }
3036
3037 leaveModal_sys(widget);
3038
3039 windows = QApplication::topLevelWidgets();
3040 QEvent e(QEvent::WindowUnblocked);
3041 for (int i = 0; i < windows.count(); ++i) {
3042 QWidget *window = windows.at(i);
3043 if(blocked.contains(window) && window->windowType() != Qt::Tool && !isBlockedByModal(window))
3044 QApplication::sendEvent(window, &e);
3045 }
3046}
3047
3048
3049
3050/*!\internal
3051
3052 Called from qapplication_\e{platform}.cpp, returns true
3053 if the widget should accept the event.
3054 */
3055bool QApplicationPrivate::tryModalHelper(QWidget *widget, QWidget **rettop)
3056{
3057 QWidget *top = QApplication::activeModalWidget();
3058 if (rettop)
3059 *rettop = top;
3060
3061 // the active popup widget always gets the input event
3062 if (QApplication::activePopupWidget())
3063 return true;
3064
3065#if defined(Q_WS_MAC) && defined(QT_MAC_USE_COCOA)
3066 top = QApplicationPrivate::tryModalHelper_sys(top);
3067 if (rettop)
3068 *rettop = top;
3069#endif
3070
3071 return !isBlockedByModal(widget->window());
3072}
3073
3074/*
3075 \internal
3076*/
3077QWidget *QApplicationPrivate::pickMouseReceiver(QWidget *candidate, const QPoint &globalPos,
3078 QPoint &pos, QEvent::Type type,
3079 Qt::MouseButtons buttons, QWidget *buttonDown,
3080 QWidget *alienWidget)
3081{
3082 Q_ASSERT(candidate);
3083
3084 QWidget *mouseGrabber = QWidget::mouseGrabber();
3085 if (((type == QEvent::MouseMove && buttons) || (type == QEvent::MouseButtonRelease))
3086 && !buttonDown && !mouseGrabber) {
3087 return 0;
3088 }
3089
3090 if (alienWidget && alienWidget->internalWinId())
3091 alienWidget = 0;
3092
3093 QWidget *receiver = candidate;
3094
3095 if (!mouseGrabber)
3096 mouseGrabber = (buttonDown && !isBlockedByModal(buttonDown)) ? buttonDown : alienWidget;
3097
3098 if (mouseGrabber && mouseGrabber != candidate) {
3099 receiver = mouseGrabber;
3100 pos = receiver->mapFromGlobal(globalPos);
3101#ifdef ALIEN_DEBUG
3102 qDebug() << " ** receiver adjusted to:" << receiver << "pos:" << pos;
3103#endif
3104 }
3105
3106 return receiver;
3107
3108}
3109
3110/*
3111 \internal
3112*/
3113bool QApplicationPrivate::sendMouseEvent(QWidget *receiver, QMouseEvent *event,
3114 QWidget *alienWidget, QWidget *nativeWidget,
3115 QWidget **buttonDown, QPointer<QWidget> &lastMouseReceiver,
3116 bool spontaneous)
3117{
3118 Q_ASSERT(receiver);
3119 Q_ASSERT(event);
3120 Q_ASSERT(nativeWidget);
3121 Q_ASSERT(buttonDown);
3122
3123 if (alienWidget && !isAlien(alienWidget))
3124 alienWidget = 0;
3125
3126 QPointer<QWidget> receiverGuard = receiver;
3127 QPointer<QWidget> nativeGuard = nativeWidget;
3128 QPointer<QWidget> alienGuard = alienWidget;
3129 QPointer<QWidget> activePopupWidget = QApplication::activePopupWidget();
3130
3131 const bool graphicsWidget = nativeWidget->testAttribute(Qt::WA_DontShowOnScreen);
3132
3133 if (*buttonDown) {
3134 if (!graphicsWidget) {
3135 // Register the widget that shall receive a leave event
3136 // after the last button is released.
3137 if ((alienWidget || !receiver->internalWinId()) && !leaveAfterRelease && !QWidget::mouseGrabber())
3138 leaveAfterRelease = *buttonDown;
3139 if (event->type() == QEvent::MouseButtonRelease && !event->buttons())
3140 *buttonDown = 0;
3141 }
3142 } else if (lastMouseReceiver) {
3143 // Dispatch enter/leave if we move:
3144 // 1) from an alien widget to another alien widget or
3145 // from a native widget to an alien widget (first OR case)
3146 // 2) from an alien widget to a native widget (second OR case)
3147 if ((alienWidget && alienWidget != lastMouseReceiver)
3148 || (isAlien(lastMouseReceiver) && !alienWidget)) {
3149 if (activePopupWidget) {
3150 if (!QWidget::mouseGrabber())
3151 dispatchEnterLeave(alienWidget ? alienWidget : nativeWidget, lastMouseReceiver);
3152 } else {
3153 dispatchEnterLeave(receiver, lastMouseReceiver);
3154 }
3155
3156 }
3157 }
3158
3159#ifdef ALIEN_DEBUG
3160 qDebug() << "QApplicationPrivate::sendMouseEvent: receiver:" << receiver
3161 << "pos:" << event->pos() << "alien" << alienWidget << "button down"
3162 << *buttonDown << "last" << lastMouseReceiver << "leave after release"
3163 << leaveAfterRelease;
3164#endif
3165
3166 // We need this quard in case someone opens a modal dialog / popup. If that's the case
3167 // leaveAfterRelease is set to null, but we shall not update lastMouseReceiver.
3168 const bool wasLeaveAfterRelease = leaveAfterRelease != 0;
3169 bool result;
3170 if (spontaneous)
3171 result = QApplication::sendSpontaneousEvent(receiver, event);
3172 else
3173 result = QApplication::sendEvent(receiver, event);
3174
3175 if (!graphicsWidget && leaveAfterRelease && event->type() == QEvent::MouseButtonRelease
3176 && !event->buttons() && QWidget::mouseGrabber() != leaveAfterRelease) {
3177 // Dispatch enter/leave if:
3178 // 1) the mouse grabber is an alien widget
3179 // 2) the button is released on an alien widget
3180 QWidget *enter = 0;
3181 if (nativeGuard)
3182 enter = alienGuard ? alienWidget : nativeWidget;
3183 else // The receiver is typically deleted on mouse release with drag'n'drop.
3184 enter = QApplication::widgetAt(event->globalPos());
3185 dispatchEnterLeave(enter, leaveAfterRelease);
3186 leaveAfterRelease = 0;
3187 lastMouseReceiver = enter;
3188 } else if (!wasLeaveAfterRelease) {
3189 if (activePopupWidget) {
3190 if (!QWidget::mouseGrabber())
3191 lastMouseReceiver = alienGuard ? alienWidget : (nativeGuard ? nativeWidget : 0);
3192 } else {
3193 lastMouseReceiver = receiverGuard ? receiver : QApplication::widgetAt(event->globalPos());
3194 }
3195 }
3196
3197 return result;
3198}
3199
3200#if defined(Q_WS_WIN) || defined(Q_WS_X11) || defined(Q_WS_QWS) || defined(Q_WS_MAC) || defined(Q_WS_QPA)
3201/*
3202 This function should only be called when the widget changes visibility, i.e.
3203 when the \a widget is shown, hidden or deleted. This function does nothing
3204 if the widget is a top-level or native, i.e. not an alien widget. In that
3205 case enter/leave events are genereated by the underlying windowing system.
3206*/
3207extern QPointer<QWidget> qt_last_mouse_receiver;
3208extern QWidget *qt_button_down;
3209void QApplicationPrivate::sendSyntheticEnterLeave(QWidget *widget)
3210{
3211#ifndef QT_NO_CURSOR
3212#if defined(Q_WS_QWS) || defined(Q_WS_QPA)
3213 if (!widget || widget->isWindow())
3214 return;
3215#else
3216 if (!widget || widget->internalWinId() || widget->isWindow())
3217 return;
3218#endif
3219 const bool widgetInShow = widget->isVisible() && !widget->data->in_destructor;
3220 if (!widgetInShow && widget != qt_last_mouse_receiver)
3221 return; // Widget was not under the cursor when it was hidden/deleted.
3222
3223 if (widgetInShow && widget->parentWidget()->data->in_show)
3224 return; // Ingore recursive show.
3225
3226 QWidget *mouseGrabber = QWidget::mouseGrabber();
3227 if (mouseGrabber && mouseGrabber != widget)
3228 return; // Someone else has the grab; enter/leave should not occur.
3229
3230 QWidget *tlw = widget->window();
3231 if (tlw->data->in_destructor || tlw->data->is_closing)
3232 return; // Closing down the business.
3233
3234 if (widgetInShow && (!qt_last_mouse_receiver || qt_last_mouse_receiver->window() != tlw))
3235 return; // Mouse cursor not inside the widget's top-level.
3236
3237 const QPoint globalPos(QCursor::pos());
3238 QPoint pos = tlw->mapFromGlobal(globalPos);
3239
3240 // Find the current widget under the mouse. If this function was called from
3241 // the widget's destructor, we have to make sure childAt() doesn't take into
3242 // account widgets that are about to be destructed.
3243 QWidget *widgetUnderCursor = tlw->d_func()->childAt_helper(pos, widget->data->in_destructor);
3244 if (!widgetUnderCursor)
3245 widgetUnderCursor = tlw;
3246 else
3247 pos = widgetUnderCursor->mapFrom(tlw, pos);
3248
3249 if (widgetInShow && widgetUnderCursor != widget && !widget->isAncestorOf(widgetUnderCursor))
3250 return; // Mouse cursor not inside the widget or any of its children.
3251
3252 if (widget->data->in_destructor && qt_button_down == widget)
3253 qt_button_down = 0;
3254
3255 // Send enter/leave events followed by a mouse move on the entered widget.
3256 QMouseEvent e(QEvent::MouseMove, pos, globalPos, Qt::NoButton, Qt::NoButton, Qt::NoModifier);
3257 sendMouseEvent(widgetUnderCursor, &e, widgetUnderCursor, tlw, &qt_button_down, qt_last_mouse_receiver);
3258#endif // QT_NO_CURSOR
3259}
3260#endif // Q_WS_WIN || Q_WS_X11 || Q_WS_MAC
3261
3262/*!
3263 Returns the desktop widget (also called the root window).
3264
3265 The desktop may be composed of multiple screens, so it would be incorrect,
3266 for example, to attempt to \e center some widget in the desktop's geometry.
3267 QDesktopWidget has various functions for obtaining useful geometries upon
3268 the desktop, such as QDesktopWidget::screenGeometry() and
3269 QDesktopWidget::availableGeometry().
3270
3271 On X11, it is also possible to draw on the desktop.
3272*/
3273QDesktopWidget *QApplication::desktop()
3274{
3275 if (!qt_desktopWidget || // not created yet
3276 !(qt_desktopWidget->windowType() == Qt::Desktop)) { // reparented away
3277 qt_desktopWidget = new QDesktopWidget();
3278 }
3279 return qt_desktopWidget;
3280}
3281
3282#ifndef QT_NO_CLIPBOARD
3283/*!
3284 Returns a pointer to the application global clipboard.
3285
3286 \note The QApplication object should already be constructed before
3287 accessing the clipboard.
3288*/
3289QClipboard *QApplication::clipboard()
3290{
3291 if (qt_clipboard == 0) {
3292 if (!qApp) {
3293 qWarning("QApplication: Must construct a QApplication before accessing a QClipboard");
3294 return 0;
3295 }
3296 qt_clipboard = new QClipboard(0);
3297 }
3298 return qt_clipboard;
3299}
3300#endif // QT_NO_CLIPBOARD
3301
3302/*!
3303 Sets whether Qt should use the system's standard colors, fonts, etc., to
3304 \a on. By default, this is true.
3305
3306 This function must be called before creating the QApplication object, like
3307 this:
3308
3309 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 6
3310
3311 \sa desktopSettingsAware()
3312*/
3313void QApplication::setDesktopSettingsAware(bool on)
3314{
3315 QApplicationPrivate::obey_desktop_settings = on;
3316}
3317
3318/*!
3319 Returns true if Qt is set to use the system's standard colors, fonts, etc.;
3320 otherwise returns false. The default is true.
3321
3322 \sa setDesktopSettingsAware()
3323*/
3324bool QApplication::desktopSettingsAware()
3325{
3326 return QApplicationPrivate::obey_desktop_settings;
3327}
3328
3329/*!
3330 Returns the current state of the modifier keys on the keyboard. The current
3331 state is updated sychronously as the event queue is emptied of events that
3332 will spontaneously change the keyboard state (QEvent::KeyPress and
3333 QEvent::KeyRelease events).
3334
3335 It should be noted this may not reflect the actual keys held on the input
3336 device at the time of calling but rather the modifiers as last reported in
3337 one of the above events. If no keys are being held Qt::NoModifier is
3338 returned.
3339
3340 \sa mouseButtons(), queryKeyboardModifiers()
3341*/
3342
3343Qt::KeyboardModifiers QApplication::keyboardModifiers()
3344{
3345 return QApplicationPrivate::modifier_buttons;
3346}
3347
3348/*!
3349 \fn Qt::KeyboardModifiers QApplication::queryKeyboardModifiers()
3350
3351 Queries and returns the state of the modifier keys on the keyboard.
3352 Unlike keyboardModifiers, this method returns the actual keys held
3353 on the input device at the time of calling the method.
3354
3355 It does not rely on the keypress events having been received by this
3356 process, which makes it possible to check the modifiers while moving
3357 a window, for instance. Note that in most cases, you should use
3358 keyboardModifiers(), which is faster and more accurate since it contains
3359 the state of the modifiers as they were when the currently processed
3360 event was received.
3361
3362 \sa keyboardModifiers()
3363
3364 \since 4.8
3365*/
3366
3367/*!
3368 Returns the current state of the buttons on the mouse. The current state is
3369 updated syncronously as the event queue is emptied of events that will
3370 spontaneously change the mouse state (QEvent::MouseButtonPress and
3371 QEvent::MouseButtonRelease events).
3372
3373 It should be noted this may not reflect the actual buttons held on the
3374 input device at the time of calling but rather the mouse buttons as last
3375 reported in one of the above events. If no mouse buttons are being held
3376 Qt::NoButton is returned.
3377
3378 \sa keyboardModifiers()
3379*/
3380
3381Qt::MouseButtons QApplication::mouseButtons()
3382{
3383 return QApplicationPrivate::mouse_buttons;
3384}
3385
3386/*!
3387 \fn bool QApplication::isSessionRestored() const
3388
3389 Returns true if the application has been restored from an earlier
3390 \l{Session Management}{session}; otherwise returns false.
3391
3392 \sa sessionId(), commitData(), saveState()
3393*/
3394
3395
3396/*!
3397 \fn QString QApplication::sessionId() const
3398
3399 Returns the current \l{Session Management}{session's} identifier.
3400
3401 If the application has been restored from an earlier session, this
3402 identifier is the same as it was in that previous session. The session
3403 identifier is guaranteed to be unique both for different applications
3404 and for different instances of the same application.
3405
3406 \sa isSessionRestored(), sessionKey(), commitData(), saveState()
3407*/
3408
3409/*!
3410 \fn QString QApplication::sessionKey() const
3411
3412 Returns the session key in the current \l{Session Management}{session}.
3413
3414 If the application has been restored from an earlier session, this key is
3415 the same as it was when the previous session ended.
3416
3417 The session key changes with every call of commitData() or saveState().
3418
3419 \sa isSessionRestored(), sessionId(), commitData(), saveState()
3420*/
3421#ifndef QT_NO_SESSIONMANAGER
3422bool QApplication::isSessionRestored() const
3423{
3424 Q_D(const QApplication);
3425 return d->is_session_restored;
3426}
3427
3428QString QApplication::sessionId() const
3429{
3430 Q_D(const QApplication);
3431 return d->session_id;
3432}
3433
3434QString QApplication::sessionKey() const
3435{
3436 Q_D(const QApplication);
3437 return d->session_key;
3438}
3439#endif
3440
3441/*!
3442 \since 4.7.4
3443 \fn void QApplication::aboutToReleaseGpuResources()
3444
3445 This signal is emitted when application is about to release all
3446 GPU resources associated to contexts owned by application.
3447
3448 The signal is particularly useful if your application has allocated
3449 GPU resources directly apart from Qt and needs to do some last-second
3450 cleanup.
3451
3452 \warning This signal is only emitted on Symbian.
3453
3454 \sa aboutToUseGpuResources()
3455*/
3456
3457/*!
3458 \since 4.7.4
3459 \fn void QApplication::aboutToUseGpuResources()
3460
3461 This signal is emitted when application is about to use GPU resources.
3462
3463 The signal is particularly useful if your application needs to know
3464 when GPU resources are be available.
3465
3466 \warning This signal is only emitted on Symbian.
3467
3468 \sa aboutToReleaseGpuResources()
3469*/
3470
3471/*!
3472 \since 4.2
3473 \fn void QApplication::commitDataRequest(QSessionManager &manager)
3474
3475 This signal deals with \l{Session Management}{session management}. It is
3476 emitted when the QSessionManager wants the application to commit all its
3477 data.
3478
3479 Usually this means saving all open files, after getting permission from
3480 the user. Furthermore you may want to provide a means by which the user
3481 can cancel the shutdown.
3482
3483 You should not exit the application within this signal. Instead,
3484 the session manager may or may not do this afterwards, depending on the
3485 context.
3486
3487 \warning Within this signal, no user interaction is possible, \e
3488 unless you ask the \a manager for explicit permission. See
3489 QSessionManager::allowsInteraction() and
3490 QSessionManager::allowsErrorInteraction() for details and example
3491 usage.
3492
3493 \note You should use Qt::DirectConnection when connecting to this signal.
3494
3495 \sa isSessionRestored(), sessionId(), saveState(), {Session Management}
3496*/
3497
3498/*!
3499 This function deals with \l{Session Management}{session management}. It is
3500 invoked when the QSessionManager wants the application to commit all its
3501 data.
3502
3503 Usually this means saving all open files, after getting permission from the
3504 user. Furthermore you may want to provide a means by which the user can
3505 cancel the shutdown.
3506
3507 You should not exit the application within this function. Instead, the
3508 session manager may or may not do this afterwards, depending on the
3509 context.
3510
3511 \warning Within this function, no user interaction is possible, \e
3512 unless you ask the \a manager for explicit permission. See
3513 QSessionManager::allowsInteraction() and
3514 QSessionManager::allowsErrorInteraction() for details and example
3515 usage.
3516
3517 The default implementation requests interaction and sends a close event to
3518 all visible top-level widgets. If any event was rejected, the shutdown is
3519 canceled.
3520
3521 \sa isSessionRestored(), sessionId(), saveState(), {Session Management}
3522*/
3523#ifndef QT_NO_SESSIONMANAGER
3524void QApplication::commitData(QSessionManager& manager )
3525{
3526 emit commitDataRequest(manager);
3527 if (manager.allowsInteraction()) {
3528 QWidgetList done;
3529 QWidgetList list = QApplication::topLevelWidgets();
3530 bool cancelled = false;
3531 for (int i = 0; !cancelled && i < list.size(); ++i) {
3532 QWidget* w = list.at(i);
3533 if (w->isVisible() && !done.contains(w)) {
3534 cancelled = !w->close();
3535 if (!cancelled)
3536 done.append(w);
3537 list = QApplication::topLevelWidgets();
3538 i = -1;
3539 }
3540 }
3541 if (cancelled)
3542 manager.cancel();
3543 }
3544}
3545
3546/*!
3547 \since 4.2
3548 \fn void QApplication::saveStateRequest(QSessionManager &manager)
3549
3550 This signal deals with \l{Session Management}{session management}. It is
3551 invoked when the \l{QSessionManager}{session manager} wants the application
3552 to preserve its state for a future session.
3553
3554 For example, a text editor would create a temporary file that includes the
3555 current contents of its edit buffers, the location of the cursor and other
3556 aspects of the current editing session.
3557
3558 You should never exit the application within this signal. Instead, the
3559 session manager may or may not do this afterwards, depending on the
3560 context. Futhermore, most session managers will very likely request a saved
3561 state immediately after the application has been started. This permits the
3562 session manager to learn about the application's restart policy.
3563
3564 \warning Within this function, no user interaction is possible, \e
3565 unless you ask the \a manager for explicit permission. See
3566 QSessionManager::allowsInteraction() and
3567 QSessionManager::allowsErrorInteraction() for details.
3568
3569 \note You should use Qt::DirectConnection when connecting to this signal.
3570
3571 \sa isSessionRestored(), sessionId(), commitData(), {Session Management}
3572*/
3573
3574/*!
3575 This function deals with \l{Session Management}{session management}. It is
3576 invoked when the \l{QSessionManager}{session manager} wants the application
3577 to preserve its state for a future session.
3578
3579 For example, a text editor would create a temporary file that includes the
3580 current contents of its edit buffers, the location of the cursor and other
3581 aspects of the current editing session.
3582
3583 You should never exit the application within this function. Instead, the
3584 session manager may or may not do this afterwards, depending on the
3585 context. Futhermore, most session managers will very likely request a saved
3586 state immediately after the application has been started. This permits the
3587 session manager to learn about the application's restart policy.
3588
3589 \warning Within this function, no user interaction is possible, \e
3590 unless you ask the \a manager for explicit permission. See
3591 QSessionManager::allowsInteraction() and
3592 QSessionManager::allowsErrorInteraction() for details.
3593
3594 \sa isSessionRestored(), sessionId(), commitData(), {Session Management}
3595*/
3596
3597void QApplication::saveState(QSessionManager &manager)
3598{
3599 emit saveStateRequest(manager);
3600}
3601#endif //QT_NO_SESSIONMANAGER
3602/*
3603 Sets the time after which a drag should start to \a ms ms.
3604
3605 \sa startDragTime()
3606*/
3607
3608void QApplication::setStartDragTime(int ms)
3609{
3610 drag_time = ms;
3611}
3612
3613/*!
3614 \property QApplication::startDragTime
3615 \brief the time in milliseconds that a mouse button must be held down
3616 before a drag and drop operation will begin
3617
3618 If you support drag and drop in your application, and want to start a drag
3619 and drop operation after the user has held down a mouse button for a
3620 certain amount of time, you should use this property's value as the delay.
3621
3622 Qt also uses this delay internally, e.g. in QTextEdit and QLineEdit, for
3623 starting a drag.
3624
3625 The default value is 500 ms.
3626
3627 \sa startDragDistance(), {Drag and Drop}
3628*/
3629
3630int QApplication::startDragTime()
3631{
3632 return drag_time;
3633}
3634
3635/*
3636 Sets the distance after which a drag should start to \a l pixels.
3637
3638 \sa startDragDistance()
3639*/
3640
3641void QApplication::setStartDragDistance(int l)
3642{
3643 drag_distance = l;
3644}
3645
3646/*!
3647 \property QApplication::startDragDistance
3648
3649 If you support drag and drop in your application, and want to start a drag
3650 and drop operation after the user has moved the cursor a certain distance
3651 with a button held down, you should use this property's value as the
3652 minimum distance required.
3653
3654 For example, if the mouse position of the click is stored in \c startPos
3655 and the current position (e.g. in the mouse move event) is \c currentPos,
3656 you can find out if a drag should be started with code like this:
3657
3658 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 7
3659
3660 Qt uses this value internally, e.g. in QFileDialog.
3661
3662 The default value is 4 pixels.
3663
3664 \sa startDragTime() QPoint::manhattanLength() {Drag and Drop}
3665*/
3666
3667int QApplication::startDragDistance()
3668{
3669 return drag_distance;
3670}
3671
3672/*!
3673 \fn void QApplication::setReverseLayout(bool reverse)
3674
3675 Use setLayoutDirection() instead.
3676*/
3677
3678/*!
3679 \fn void QApplication::reverseLayout()
3680
3681 Use layoutDirection() instead.
3682*/
3683
3684/*!
3685 \fn bool QApplication::isRightToLeft()
3686
3687 Returns true if the application's layout direction is
3688 Qt::RightToLeft; otherwise returns false.
3689
3690 \sa layoutDirection(), isLeftToRight()
3691*/
3692
3693/*!
3694 \fn bool QApplication::isLeftToRight()
3695
3696 Returns true if the application's layout direction is
3697 Qt::LeftToRight; otherwise returns false.
3698
3699 \sa layoutDirection(), isRightToLeft()
3700*/
3701
3702/*!
3703 \property QApplication::layoutDirection
3704 \brief the default layout direction for this application
3705
3706 On system start-up, the default layout direction depends on the
3707 application's language.
3708
3709 \sa QWidget::layoutDirection, isLeftToRight(), isRightToLeft()
3710 */
3711
3712void QApplication::setLayoutDirection(Qt::LayoutDirection direction)
3713{
3714 if (layout_direction == direction || direction == Qt::LayoutDirectionAuto)
3715 return;
3716
3717 layout_direction = direction;
3718
3719 QWidgetList list = topLevelWidgets();
3720 for (int i = 0; i < list.size(); ++i) {
3721 QWidget *w = list.at(i);
3722 QEvent ev(QEvent::ApplicationLayoutDirectionChange);
3723 sendEvent(w, &ev);
3724 }
3725}
3726
3727Qt::LayoutDirection QApplication::layoutDirection()
3728{
3729 return layout_direction;
3730}
3731
3732
3733/*!
3734 \obsolete
3735
3736 Strips out vertical alignment flags and transforms an alignment \a align
3737 of Qt::AlignLeft into Qt::AlignLeft or Qt::AlignRight according to the
3738 language used.
3739*/
3740
3741#ifdef QT3_SUPPORT
3742Qt::Alignment QApplication::horizontalAlignment(Qt::Alignment align)
3743{
3744 return QStyle::visualAlignment(layoutDirection(), align);
3745}
3746#endif
3747
3748
3749/*!
3750 \fn QCursor *QApplication::overrideCursor()
3751
3752 Returns the active application override cursor.
3753
3754 This function returns 0 if no application cursor has been defined (i.e. the
3755 internal cursor stack is empty).
3756
3757 \sa setOverrideCursor(), restoreOverrideCursor()
3758*/
3759#ifndef QT_NO_CURSOR
3760QCursor *QApplication::overrideCursor()
3761{
3762 return qApp->d_func()->cursor_list.isEmpty() ? 0 : &qApp->d_func()->cursor_list.first();
3763}
3764
3765/*!
3766 Changes the currently active application override cursor to \a cursor.
3767
3768 This function has no effect if setOverrideCursor() was not called.
3769
3770 \sa setOverrideCursor(), overrideCursor(), restoreOverrideCursor(),
3771 QWidget::setCursor()
3772 */
3773void QApplication::changeOverrideCursor(const QCursor &cursor)
3774{
3775 if (qApp->d_func()->cursor_list.isEmpty())
3776 return;
3777 qApp->d_func()->cursor_list.removeFirst();
3778 setOverrideCursor(cursor);
3779}
3780#endif
3781
3782/*!
3783 \fn void QApplication::setOverrideCursor(const QCursor &cursor, bool replace)
3784
3785 Use changeOverrideCursor(\a cursor) (if \a replace is true) or
3786 setOverrideCursor(\a cursor) (if \a replace is false).
3787*/
3788
3789/*!
3790 Enters the main event loop and waits until exit() is called, then returns
3791 the value that was set to exit() (which is 0 if exit() is called via
3792 quit()).
3793
3794 It is necessary to call this function to start event handling. The main
3795 event loop receives events from the window system and dispatches these to
3796 the application widgets.
3797
3798 Generally, no user interaction can take place before calling exec(). As a
3799 special case, modal widgets like QMessageBox can be used before calling
3800 exec(), because modal widgets call exec() to start a local event loop.
3801
3802 To make your application perform idle processing, i.e., executing a special
3803 function whenever there are no pending events, use a QTimer with 0 timeout.
3804 More advanced idle processing schemes can be achieved using processEvents().
3805
3806 We recommend that you connect clean-up code to the
3807 \l{QCoreApplication::}{aboutToQuit()} signal, instead of putting it in your
3808 application's \c{main()} function. This is because, on some platforms the
3809 QApplication::exec() call may not return. For example, on the Windows
3810 platform, when the user logs off, the system terminates the process after Qt
3811 closes all top-level windows. Hence, there is \e{no guarantee} that the
3812 application will have time to exit its event loop and execute code at the
3813 end of the \c{main()} function, after the QApplication::exec() call.
3814
3815 \sa quitOnLastWindowClosed, quit(), exit(), processEvents(),
3816 QCoreApplication::exec()
3817*/
3818int QApplication::exec()
3819{
3820#ifndef QT_NO_ACCESSIBILITY
3821 QAccessible::setRootObject(qApp);
3822#endif
3823 return QCoreApplication::exec();
3824}
3825
3826/*! \reimp
3827 */
3828bool QApplication::notify(QObject *receiver, QEvent *e)
3829{
3830 Q_D(QApplication);
3831 // no events are delivered after ~QCoreApplication() has started
3832 if (QApplicationPrivate::is_app_closing)
3833 return true;
3834
3835 if (receiver == 0) { // serious error
3836 qWarning("QApplication::notify: Unexpected null receiver");
3837 return true;
3838 }
3839
3840#ifndef QT_NO_DEBUG
3841 d->checkReceiverThread(receiver);
3842#endif
3843
3844 // capture the current mouse/keyboard state
3845 if(e->spontaneous()) {
3846 if (e->type() == QEvent::KeyPress
3847 || e->type() == QEvent::KeyRelease) {
3848 QKeyEvent *ke = static_cast<QKeyEvent*>(e);
3849 QApplicationPrivate::modifier_buttons = ke->modifiers();
3850 } else if(e->type() == QEvent::MouseButtonPress
3851 || e->type() == QEvent::MouseButtonRelease) {
3852 QMouseEvent *me = static_cast<QMouseEvent*>(e);
3853 QApplicationPrivate::modifier_buttons = me->modifiers();
3854 if(me->type() == QEvent::MouseButtonPress)
3855 QApplicationPrivate::mouse_buttons |= me->button();
3856 else
3857 QApplicationPrivate::mouse_buttons &= ~me->button();
3858 }
3859#if !defined(QT_NO_WHEELEVENT) || !defined(QT_NO_TABLETEVENT)
3860 else if (false
3861# ifndef QT_NO_WHEELEVENT
3862 || e->type() == QEvent::Wheel
3863# endif
3864# ifndef QT_NO_TABLETEVENT
3865 || e->type() == QEvent::TabletMove
3866 || e->type() == QEvent::TabletPress
3867 || e->type() == QEvent::TabletRelease
3868# endif
3869 ) {
3870 QInputEvent *ie = static_cast<QInputEvent*>(e);
3871 QApplicationPrivate::modifier_buttons = ie->modifiers();
3872 }
3873#endif // !QT_NO_WHEELEVENT || !QT_NO_TABLETEVENT
3874 }
3875
3876#ifndef QT_NO_GESTURES
3877 // walk through parents and check for gestures
3878 if (d->gestureManager) {
3879 switch (e->type()) {
3880 case QEvent::Paint:
3881 case QEvent::MetaCall:
3882 case QEvent::DeferredDelete:
3883 case QEvent::DragEnter: case QEvent::DragMove: case QEvent::DragLeave:
3884 case QEvent::Drop: case QEvent::DragResponse:
3885 case QEvent::ChildAdded: case QEvent::ChildPolished:
3886#ifdef QT3_SUPPORT
3887 case QEvent::ChildInsertedRequest:
3888 case QEvent::ChildInserted:
3889 case QEvent::LayoutHint:
3890#endif
3891 case QEvent::ChildRemoved:
3892 case QEvent::UpdateRequest:
3893 case QEvent::UpdateLater:
3894 case QEvent::AccessibilityPrepare:
3895 case QEvent::LocaleChange:
3896 case QEvent::Style:
3897 case QEvent::IconDrag:
3898 case QEvent::StyleChange:
3899 case QEvent::AccessibilityHelp:
3900 case QEvent::AccessibilityDescription:
3901 case QEvent::GraphicsSceneDragEnter:
3902 case QEvent::GraphicsSceneDragMove:
3903 case QEvent::GraphicsSceneDragLeave:
3904 case QEvent::GraphicsSceneDrop:
3905 case QEvent::DynamicPropertyChange:
3906 case QEvent::NetworkReplyUpdated:
3907 break;
3908 default:
3909 if (d->gestureManager->thread() == QThread::currentThread()) {
3910 if (receiver->isWidgetType()) {
3911 if (d->gestureManager->filterEvent(static_cast<QWidget *>(receiver), e))
3912 return true;
3913 } else {
3914 // a special case for events that go to QGesture objects.
3915 // We pass the object to the gesture manager and it'll figure
3916 // out if it's QGesture or not.
3917 if (d->gestureManager->filterEvent(receiver, e))
3918 return true;
3919 }
3920 }
3921 break;
3922 }
3923 }
3924#endif // QT_NO_GESTURES
3925
3926 // User input and window activation makes tooltips sleep
3927 switch (e->type()) {
3928 case QEvent::Wheel:
3929 case QEvent::ActivationChange:
3930 case QEvent::KeyPress:
3931 case QEvent::KeyRelease:
3932 case QEvent::FocusOut:
3933 case QEvent::FocusIn:
3934 case QEvent::MouseButtonPress:
3935 case QEvent::MouseButtonRelease:
3936 case QEvent::MouseButtonDblClick:
3937 d->toolTipFallAsleep.stop();
3938 // fall-through
3939 case QEvent::Leave:
3940 d->toolTipWakeUp.stop();
3941 default:
3942 break;
3943 }
3944
3945 bool res = false;
3946 if (!receiver->isWidgetType()) {
3947 res = d->notify_helper(receiver, e);
3948 } else switch (e->type()) {
3949#if defined QT3_SUPPORT && !defined(QT_NO_SHORTCUT)
3950 case QEvent::Accel:
3951 {
3952 if (d->use_compat()) {
3953 QKeyEvent* key = static_cast<QKeyEvent*>(e);
3954 res = d->notify_helper(receiver, e);
3955
3956 if (!res && !key->isAccepted())
3957 res = d->qt_dispatchAccelEvent(static_cast<QWidget *>(receiver), key);
3958
3959 // next lines are for compatibility with Qt <= 3.0.x: old
3960 // QAccel was listening on toplevel widgets
3961 if (!res && !key->isAccepted() && !static_cast<QWidget *>(receiver)->isWindow())
3962 res = d->notify_helper(static_cast<QWidget *>(receiver)->window(), e);
3963 }
3964 break;
3965 }
3966#endif //QT3_SUPPORT && !QT_NO_SHORTCUT
3967 case QEvent::ShortcutOverride:
3968 case QEvent::KeyPress:
3969 case QEvent::KeyRelease:
3970 {
3971 bool isWidget = receiver->isWidgetType();
3972 bool isGraphicsWidget = false;
3973#ifndef QT_NO_GRAPHICSVIEW
3974 isGraphicsWidget = !isWidget && qobject_cast<QGraphicsWidget *>(receiver);
3975#endif
3976 if (!isWidget && !isGraphicsWidget) {
3977 res = d->notify_helper(receiver, e);
3978 break;
3979 }
3980
3981 QKeyEvent* key = static_cast<QKeyEvent*>(e);
3982#if defined QT3_SUPPORT && !defined(QT_NO_SHORTCUT)
3983 if (d->use_compat() && d->qt_tryComposeUnicode(static_cast<QWidget*>(receiver), key))
3984 break;
3985#endif
3986 if (key->type()==QEvent::KeyPress) {
3987#ifndef QT_NO_SHORTCUT
3988 // Try looking for a Shortcut before sending key events
3989 if ((res = qApp->d_func()->shortcutMap.tryShortcutEvent(receiver, key)))
3990 return res;
3991#endif
3992 qt_in_tab_key_event = (key->key() == Qt::Key_Backtab
3993 || key->key() == Qt::Key_Tab
3994 || key->key() == Qt::Key_Left
3995 || key->key() == Qt::Key_Up
3996 || key->key() == Qt::Key_Right
3997 || key->key() == Qt::Key_Down);
3998 }
3999 bool def = key->isAccepted();
4000 QPointer<QObject> pr = receiver;
4001 while (receiver) {
4002 if (def)
4003 key->accept();
4004 else
4005 key->ignore();
4006 res = d->notify_helper(receiver, e);
4007 QWidget *w = isWidget ? static_cast<QWidget *>(receiver) : 0;
4008#ifndef QT_NO_GRAPHICSVIEW
4009 QGraphicsWidget *gw = isGraphicsWidget ? static_cast<QGraphicsWidget *>(receiver) : 0;
4010#endif
4011
4012 if ((res && key->isAccepted())
4013 /*
4014 QLineEdit will emit a signal on Key_Return, but
4015 ignore the event, and sometimes the connected
4016 slot deletes the QLineEdit (common in itemview
4017 delegates), so we have to check if the widget
4018 was destroyed even if the event was ignored (to
4019 prevent a crash)
4020
4021 note that we don't have to reset pw while
4022 propagating (because the original receiver will
4023 be destroyed if one of its ancestors is)
4024 */
4025 || !pr
4026 || (isWidget && (w->isWindow() || !w->parentWidget()))
4027#ifndef QT_NO_GRAPHICSVIEW
4028 || (isGraphicsWidget && (gw->isWindow() || !gw->parentWidget()))
4029#endif
4030 ) {
4031 break;
4032 }
4033
4034#ifndef QT_NO_GRAPHICSVIEW
4035 receiver = w ? (QObject *)w->parentWidget() : (QObject *)gw->parentWidget();
4036#else
4037 receiver = w->parentWidget();
4038#endif
4039 }
4040 qt_in_tab_key_event = false;
4041 }
4042 break;
4043 case QEvent::MouseButtonPress:
4044 case QEvent::MouseButtonRelease:
4045 case QEvent::MouseButtonDblClick:
4046 case QEvent::MouseMove:
4047 {
4048 QWidget* w = static_cast<QWidget *>(receiver);
4049
4050 QMouseEvent* mouse = static_cast<QMouseEvent*>(e);
4051 QPoint relpos = mouse->pos();
4052
4053 if (e->spontaneous()) {
4054#ifndef QT_NO_IM
4055 QInputContext *ic = w->inputContext();
4056 if (ic
4057 && w->testAttribute(Qt::WA_InputMethodEnabled)
4058 && ic->filterEvent(mouse))
4059 return true;
4060#endif
4061
4062 if (e->type() == QEvent::MouseButtonPress) {
4063 QApplicationPrivate::giveFocusAccordingToFocusPolicy(w,
4064 Qt::ClickFocus,
4065 Qt::MouseFocusReason);
4066 }
4067
4068 // ### Qt 5 These dynamic tool tips should be an OPT-IN feature. Some platforms
4069 // like Mac OS X (probably others too), can optimize their views by not
4070 // dispatching mouse move events. We have attributes to control hover,
4071 // and mouse tracking, but as long as we are deciding to implement this
4072 // feature without choice of opting-in or out, you ALWAYS have to have
4073 // tracking enabled. Therefore, the other properties give a false sense of
4074 // performance enhancement.
4075 if (e->type() == QEvent::MouseMove && mouse->buttons() == 0) {
4076 d->toolTipWidget = w;
4077 d->toolTipPos = relpos;
4078 d->toolTipGlobalPos = mouse->globalPos();
4079 d->toolTipWakeUp.start(d->toolTipFallAsleep.isActive()?20:700, this);
4080 }
4081 }
4082
4083 bool eventAccepted = mouse->isAccepted();
4084
4085 QPointer<QWidget> pw = w;
4086 while (w) {
4087 QMouseEvent me(mouse->type(), relpos, mouse->globalPos(), mouse->button(), mouse->buttons(),
4088 mouse->modifiers());
4089 me.spont = mouse->spontaneous();
4090 // throw away any mouse-tracking-only mouse events
4091 if (!w->hasMouseTracking()
4092 && mouse->type() == QEvent::MouseMove && mouse->buttons() == 0) {
4093 // but still send them through all application event filters (normally done by notify_helper)
4094 for (int i = 0; i < d->eventFilters.size(); ++i) {
4095 register QObject *obj = d->eventFilters.at(i);
4096 if (!obj)
4097 continue;
4098 if (obj->d_func()->threadData != w->d_func()->threadData) {
4099 qWarning("QApplication: Object event filter cannot be in a different thread.");
4100 continue;
4101 }
4102 if (obj->eventFilter(w, w == receiver ? mouse : &me))
4103 break;
4104 }
4105 res = true;
4106 } else {
4107 w->setAttribute(Qt::WA_NoMouseReplay, false);
4108 res = d->notify_helper(w, w == receiver ? mouse : &me);
4109 e->spont = false;
4110 }
4111 eventAccepted = (w == receiver ? mouse : &me)->isAccepted();
4112 if (res && eventAccepted)
4113 break;
4114 if (w->isWindow() || w->testAttribute(Qt::WA_NoMousePropagation))
4115 break;
4116 relpos += w->pos();
4117 w = w->parentWidget();
4118 }
4119
4120 mouse->setAccepted(eventAccepted);
4121
4122 if (e->type() == QEvent::MouseMove) {
4123 if (!pw)
4124 break;
4125
4126 w = static_cast<QWidget *>(receiver);
4127 relpos = mouse->pos();
4128 QPoint diff = relpos - w->mapFromGlobal(d->hoverGlobalPos);
4129 while (w) {
4130 if (w->testAttribute(Qt::WA_Hover) &&
4131 (!QApplication::activePopupWidget() || QApplication::activePopupWidget() == w->window())) {
4132 QHoverEvent he(QEvent::HoverMove, relpos, relpos - diff);
4133 d->notify_helper(w, &he);
4134 }
4135 if (w->isWindow() || w->testAttribute(Qt::WA_NoMousePropagation))
4136 break;
4137 relpos += w->pos();
4138 w = w->parentWidget();
4139 }
4140 }
4141
4142 d->hoverGlobalPos = mouse->globalPos();
4143 }
4144 break;
4145#ifndef QT_NO_WHEELEVENT
4146 case QEvent::Wheel:
4147 {
4148 QWidget* w = static_cast<QWidget *>(receiver);
4149 QWheelEvent* wheel = static_cast<QWheelEvent*>(e);
4150 QPoint relpos = wheel->pos();
4151 bool eventAccepted = wheel->isAccepted();
4152
4153 if (e->spontaneous()) {
4154 QApplicationPrivate::giveFocusAccordingToFocusPolicy(w,
4155 Qt::WheelFocus,
4156 Qt::MouseFocusReason);
4157 }
4158
4159 while (w) {
4160 QWheelEvent we(relpos, wheel->globalPos(), wheel->delta(), wheel->buttons(),
4161 wheel->modifiers(), wheel->orientation());
4162 we.spont = wheel->spontaneous();
4163 res = d->notify_helper(w, w == receiver ? wheel : &we);
4164 eventAccepted = ((w == receiver) ? wheel : &we)->isAccepted();
4165 e->spont = false;
4166 if ((res && eventAccepted)
4167 || w->isWindow() || w->testAttribute(Qt::WA_NoMousePropagation))
4168 break;
4169
4170 relpos += w->pos();
4171 w = w->parentWidget();
4172 }
4173 wheel->setAccepted(eventAccepted);
4174 }
4175 break;
4176#endif
4177#ifndef QT_NO_CONTEXTMENU
4178 case QEvent::ContextMenu:
4179 {
4180 QWidget* w = static_cast<QWidget *>(receiver);
4181 QContextMenuEvent *context = static_cast<QContextMenuEvent*>(e);
4182 QPoint relpos = context->pos();
4183 bool eventAccepted = context->isAccepted();
4184 while (w) {
4185 QContextMenuEvent ce(context->reason(), relpos, context->globalPos(), context->modifiers());
4186 ce.spont = e->spontaneous();
4187 res = d->notify_helper(w, w == receiver ? context : &ce);
4188 eventAccepted = ((w == receiver) ? context : &ce)->isAccepted();
4189 e->spont = false;
4190
4191 if ((res && eventAccepted)
4192 || w->isWindow() || w->testAttribute(Qt::WA_NoMousePropagation))
4193 break;
4194
4195 relpos += w->pos();
4196 w = w->parentWidget();
4197 }
4198 context->setAccepted(eventAccepted);
4199 }
4200 break;
4201#endif // QT_NO_CONTEXTMENU
4202#ifndef QT_NO_TABLETEVENT
4203 case QEvent::TabletMove:
4204 case QEvent::TabletPress:
4205 case QEvent::TabletRelease:
4206 {
4207 QWidget *w = static_cast<QWidget *>(receiver);
4208 QTabletEvent *tablet = static_cast<QTabletEvent*>(e);
4209 QPoint relpos = tablet->pos();
4210 bool eventAccepted = tablet->isAccepted();
4211 while (w) {
4212 QTabletEvent te(tablet->type(), relpos, tablet->globalPos(),
4213 tablet->hiResGlobalPos(), tablet->device(), tablet->pointerType(),
4214 tablet->pressure(), tablet->xTilt(), tablet->yTilt(),
4215 tablet->tangentialPressure(), tablet->rotation(), tablet->z(),
4216 tablet->modifiers(), tablet->uniqueId());
4217 te.spont = e->spontaneous();
4218 res = d->notify_helper(w, w == receiver ? tablet : &te);
4219 eventAccepted = ((w == receiver) ? tablet : &te)->isAccepted();
4220 e->spont = false;
4221 if ((res && eventAccepted)
4222 || w->isWindow()
4223 || w->testAttribute(Qt::WA_NoMousePropagation))
4224 break;
4225
4226 relpos += w->pos();
4227 w = w->parentWidget();
4228 }
4229 tablet->setAccepted(eventAccepted);
4230 qt_tabletChokeMouse = tablet->isAccepted();
4231 }
4232 break;
4233#endif // QT_NO_TABLETEVENT
4234
4235#if !defined(QT_NO_TOOLTIP) || !defined(QT_NO_WHATSTHIS)
4236 case QEvent::ToolTip:
4237 case QEvent::WhatsThis:
4238 case QEvent::QueryWhatsThis:
4239 {
4240 QWidget* w = static_cast<QWidget *>(receiver);
4241 QHelpEvent *help = static_cast<QHelpEvent*>(e);
4242 QPoint relpos = help->pos();
4243 bool eventAccepted = help->isAccepted();
4244 while (w) {
4245 QHelpEvent he(help->type(), relpos, help->globalPos());
4246 he.spont = e->spontaneous();
4247 res = d->notify_helper(w, w == receiver ? help : &he);
4248 e->spont = false;
4249 eventAccepted = (w == receiver ? help : &he)->isAccepted();
4250 if ((res && eventAccepted) || w->isWindow())
4251 break;
4252
4253 relpos += w->pos();
4254 w = w->parentWidget();
4255 }
4256 help->setAccepted(eventAccepted);
4257 }
4258 break;
4259#endif
4260#if !defined(QT_NO_STATUSTIP) || !defined(QT_NO_WHATSTHIS)
4261 case QEvent::StatusTip:
4262 case QEvent::WhatsThisClicked:
4263 {
4264 QWidget *w = static_cast<QWidget *>(receiver);
4265 while (w) {
4266 res = d->notify_helper(w, e);
4267 if ((res && e->isAccepted()) || w->isWindow())
4268 break;
4269 w = w->parentWidget();
4270 }
4271 }
4272 break;
4273#endif
4274
4275#ifndef QT_NO_DRAGANDDROP
4276 case QEvent::DragEnter: {
4277 QWidget* w = static_cast<QWidget *>(receiver);
4278 QDragEnterEvent *dragEvent = static_cast<QDragEnterEvent *>(e);
4279#ifdef Q_WS_MAC
4280 // HIView has a slight difference in how it delivers events to children and parents
4281 // It will not give a leave to a child's parent when it enters a child.
4282 QWidget *currentTarget = QDragManager::self()->currentTarget();
4283 if (currentTarget) {
4284 // Assume currentTarget did not get a leave
4285 QDragLeaveEvent event;
4286 QApplication::sendEvent(currentTarget, &event);
4287 }
4288#endif
4289#ifndef QT_NO_GRAPHICSVIEW
4290 // QGraphicsProxyWidget handles its own propagation,
4291 // and we must not change QDragManagers currentTarget.
4292 QWExtra *extra = w->window()->d_func()->extra;
4293 if (extra && extra->proxyWidget) {
4294 res = d->notify_helper(w, dragEvent);
4295 break;
4296 }
4297#endif
4298 while (w) {
4299 if (w->isEnabled() && w->acceptDrops()) {
4300 res = d->notify_helper(w, dragEvent);
4301 if (res && dragEvent->isAccepted()) {
4302 QDragManager::self()->setCurrentTarget(w);
4303 break;
4304 }
4305 }
4306 if (w->isWindow())
4307 break;
4308 dragEvent->p = w->mapToParent(dragEvent->p);
4309 w = w->parentWidget();
4310 }
4311 }
4312 break;
4313 case QEvent::DragMove:
4314 case QEvent::Drop:
4315 case QEvent::DragLeave: {
4316 QWidget* w = static_cast<QWidget *>(receiver);
4317#ifndef QT_NO_GRAPHICSVIEW
4318 // QGraphicsProxyWidget handles its own propagation,
4319 // and we must not change QDragManagers currentTarget.
4320 QWExtra *extra = w->window()->d_func()->extra;
4321 bool isProxyWidget = extra && extra->proxyWidget;
4322 if (!isProxyWidget)
4323#endif
4324 w = QDragManager::self()->currentTarget();
4325
4326 if (!w) {
4327#ifdef Q_WS_MAC
4328 // HIView has a slight difference in how it delivers events to children and parents
4329 // It will not give an enter to a child's parent when it leaves the child.
4330 if (e->type() == QEvent::DragLeave)
4331 break;
4332 // Assume that w did not get an enter.
4333 QDropEvent *dropEvent = static_cast<QDropEvent *>(e);
4334 QDragEnterEvent dragEnterEvent(dropEvent->pos(), dropEvent->possibleActions(),
4335 dropEvent->mimeData(), dropEvent->mouseButtons(),
4336 dropEvent->keyboardModifiers());
4337 QApplication::sendEvent(receiver, &dragEnterEvent);
4338 w = QDragManager::self()->currentTarget();
4339 if (!w)
4340#endif
4341 break;
4342 }
4343 if (e->type() == QEvent::DragMove || e->type() == QEvent::Drop) {
4344 QDropEvent *dragEvent = static_cast<QDropEvent *>(e);
4345 QWidget *origReciver = static_cast<QWidget *>(receiver);
4346 while (origReciver && w != origReciver) {
4347 dragEvent->p = origReciver->mapToParent(dragEvent->p);
4348 origReciver = origReciver->parentWidget();
4349 }
4350 }
4351 res = d->notify_helper(w, e);
4352 if (e->type() != QEvent::DragMove
4353#ifndef QT_NO_GRAPHICSVIEW
4354 && !isProxyWidget
4355#endif
4356 )
4357 QDragManager::self()->setCurrentTarget(0, e->type() == QEvent::Drop);
4358 }
4359 break;
4360#endif
4361 case QEvent::TouchBegin:
4362 // Note: TouchUpdate and TouchEnd events are never propagated
4363 {
4364 QWidget *widget = static_cast<QWidget *>(receiver);
4365 QTouchEvent *touchEvent = static_cast<QTouchEvent *>(e);
4366 bool eventAccepted = touchEvent->isAccepted();
4367 if (widget->testAttribute(Qt::WA_AcceptTouchEvents) && e->spontaneous()) {
4368 // give the widget focus if the focus policy allows it
4369 QApplicationPrivate::giveFocusAccordingToFocusPolicy(widget,
4370 Qt::ClickFocus,
4371 Qt::MouseFocusReason);
4372 }
4373
4374 while (widget) {
4375 // first, try to deliver the touch event
4376 bool acceptTouchEvents = widget->testAttribute(Qt::WA_AcceptTouchEvents);
4377 touchEvent->setWidget(widget);
4378 touchEvent->setAccepted(acceptTouchEvents);
4379 QWeakPointer<QWidget> p = widget;
4380 res = acceptTouchEvents && d->notify_helper(widget, touchEvent);
4381 eventAccepted = touchEvent->isAccepted();
4382 if (p.isNull()) {
4383 // widget was deleted
4384 widget = 0;
4385 } else {
4386 widget->setAttribute(Qt::WA_WState_AcceptedTouchBeginEvent, res && eventAccepted);
4387 }
4388 touchEvent->spont = false;
4389 if (res && eventAccepted) {
4390 // the first widget to accept the TouchBegin gets an implicit grab.
4391 for (int i = 0; i < touchEvent->touchPoints().count(); ++i) {
4392 const QTouchEvent::TouchPoint &touchPoint = touchEvent->touchPoints().at(i);
4393 d->widgetForTouchPointId[touchPoint.id()] = widget;
4394 }
4395 break;
4396 } else if (p.isNull() || widget->isWindow() || widget->testAttribute(Qt::WA_NoMousePropagation)) {
4397 break;
4398 }
4399 QPoint offset = widget->pos();
4400 widget = widget->parentWidget();
4401 touchEvent->setWidget(widget);
4402 for (int i = 0; i < touchEvent->_touchPoints.size(); ++i) {
4403 QTouchEvent::TouchPoint &pt = touchEvent->_touchPoints[i];
4404 QRectF rect = pt.rect();
4405 rect.moveCenter(offset);
4406 pt.d->rect = rect;
4407 pt.d->startPos = pt.startPos() + offset;
4408 pt.d->lastPos = pt.lastPos() + offset;
4409 }
4410 }
4411
4412 touchEvent->setAccepted(eventAccepted);
4413 break;
4414 }
4415 case QEvent::RequestSoftwareInputPanel:
4416 case QEvent::CloseSoftwareInputPanel:
4417#ifndef QT_NO_IM
4418 if (receiver->isWidgetType()) {
4419 QWidget *w = static_cast<QWidget *>(receiver);
4420 QInputContext *ic = w->inputContext();
4421 if (ic && ic->filterEvent(e)) {
4422 break;
4423 }
4424 }
4425#endif
4426 res = d->notify_helper(receiver, e);
4427 break;
4428
4429#ifndef QT_NO_GESTURES
4430 case QEvent::NativeGesture:
4431 {
4432 // only propagate the first gesture event (after the GID_BEGIN)
4433 QWidget *w = static_cast<QWidget *>(receiver);
4434 while (w) {
4435 e->ignore();
4436 res = d->notify_helper(w, e);
4437 if ((res && e->isAccepted()) || w->isWindow())
4438 break;
4439 w = w->parentWidget();
4440 }
4441 break;
4442 }
4443 case QEvent::Gesture:
4444 case QEvent::GestureOverride:
4445 {
4446 if (receiver->isWidgetType()) {
4447 QWidget *w = static_cast<QWidget *>(receiver);
4448 QGestureEvent *gestureEvent = static_cast<QGestureEvent *>(e);
4449 QList<QGesture *> allGestures = gestureEvent->gestures();
4450
4451 bool eventAccepted = gestureEvent->isAccepted();
4452 bool wasAccepted = eventAccepted;
4453 while (w) {
4454 // send only gestures the widget expects
4455 QList<QGesture *> gestures;
4456 QWidgetPrivate *wd = w->d_func();
4457 for (int i = 0; i < allGestures.size();) {
4458 QGesture *g = allGestures.at(i);
4459 Qt::GestureType type = g->gestureType();
4460 QMap<Qt::GestureType, Qt::GestureFlags>::iterator contextit =
4461 wd->gestureContext.find(type);
4462 bool deliver = contextit != wd->gestureContext.end() &&
4463 (g->state() == Qt::GestureStarted || w == receiver ||
4464 (contextit.value() & Qt::ReceivePartialGestures));
4465 if (deliver) {
4466 allGestures.removeAt(i);
4467 gestures.append(g);
4468 } else {
4469 ++i;
4470 }
4471 }
4472 if (!gestures.isEmpty()) { // we have gestures for this w
4473 QGestureEvent ge(gestures);
4474 ge.t = gestureEvent->t;
4475 ge.spont = gestureEvent->spont;
4476 ge.m_accept = wasAccepted;
4477 ge.d_func()->accepted = gestureEvent->d_func()->accepted;
4478 res = d->notify_helper(w, &ge);
4479 gestureEvent->spont = false;
4480 eventAccepted = ge.isAccepted();
4481 for (int i = 0; i < gestures.size(); ++i) {
4482 QGesture *g = gestures.at(i);
4483 // Ignore res [event return value] because handling of multiple gestures
4484 // packed into a single QEvent depends on not consuming the event
4485 if (eventAccepted || ge.isAccepted(g)) {
4486 // if the gesture was accepted, mark the target widget for it
4487 gestureEvent->d_func()->targetWidgets[g->gestureType()] = w;
4488 gestureEvent->setAccepted(g, true);
4489 } else {
4490 // if the gesture was explicitly ignored by the application,
4491 // put it back so a parent can get it
4492 allGestures.append(g);
4493 }
4494 }
4495 }
4496 if (allGestures.isEmpty()) // everything delivered
4497 break;
4498 if (w->isWindow())
4499 break;
4500 w = w->parentWidget();
4501 }
4502 foreach (QGesture *g, allGestures)
4503 gestureEvent->setAccepted(g, false);
4504 gestureEvent->m_accept = false; // to make sure we check individual gestures
4505 } else {
4506 res = d->notify_helper(receiver, e);
4507 }
4508 break;
4509 }
4510#endif // QT_NO_GESTURES
4511#ifdef QT_MAC_USE_COCOA
4512 case QEvent::Enter:
4513 if (receiver->isWidgetType()) {
4514 QWidget *w = static_cast<QWidget *>(receiver);
4515 if (w->testAttribute(Qt::WA_AcceptTouchEvents))
4516 qt_widget_private(w)->registerTouchWindow(true);
4517 }
4518 res = d->notify_helper(receiver, e);
4519 break;
4520 case QEvent::Leave:
4521 if (receiver->isWidgetType()) {
4522 QWidget *w = static_cast<QWidget *>(receiver);
4523 if (w->testAttribute(Qt::WA_AcceptTouchEvents))
4524 qt_widget_private(w)->registerTouchWindow(false);
4525 }
4526 res = d->notify_helper(receiver, e);
4527 break;
4528#endif
4529 default:
4530 res = d->notify_helper(receiver, e);
4531 break;
4532 }
4533
4534 return res;
4535}
4536
4537bool QApplicationPrivate::notify_helper(QObject *receiver, QEvent * e)
4538{
4539 // send to all application event filters
4540 if (sendThroughApplicationEventFilters(receiver, e))
4541 return true;
4542
4543 if (receiver->isWidgetType()) {
4544 QWidget *widget = static_cast<QWidget *>(receiver);
4545
4546#if !defined(Q_WS_WINCE) || (defined(GWES_ICONCURS) && !defined(QT_NO_CURSOR))
4547 // toggle HasMouse widget state on enter and leave
4548 if ((e->type() == QEvent::Enter || e->type() == QEvent::DragEnter) &&
4549 (!QApplication::activePopupWidget() || QApplication::activePopupWidget() == widget->window()))
4550 widget->setAttribute(Qt::WA_UnderMouse, true);
4551 else if (e->type() == QEvent::Leave || e->type() == QEvent::DragLeave)
4552 widget->setAttribute(Qt::WA_UnderMouse, false);
4553#endif
4554
4555 if (QLayout *layout=widget->d_func()->layout) {
4556 layout->widgetEvent(e);
4557 }
4558 }
4559
4560 // send to all receiver event filters
4561 if (sendThroughObjectEventFilters(receiver, e))
4562 return true;
4563
4564 // deliver the event
4565 bool consumed = receiver->event(e);
4566 e->spont = false;
4567 return consumed;
4568}
4569
4570
4571/*!
4572 \class QSessionManager
4573 \brief The QSessionManager class provides access to the session manager.
4574
4575 A session manager in a desktop environment (in which Qt GUI applications
4576 live) keeps track of a session, which is a group of running applications,
4577 each of which has a particular state. The state of an application contains
4578 (most notably) the documents the application has open and the position and
4579 size of its windows.
4580
4581 The session manager is used to save the session, e.g., when the machine is
4582 shut down, and to restore a session, e.g., when the machine is started up.
4583 We recommend that you use QSettings to save an application's settings,
4584 for example, window positions, recently used files, etc. When the
4585 application is restarted by the session manager, you can restore the
4586 settings.
4587
4588 QSessionManager provides an interface between the application and the
4589 session manager so that the program can work well with the session manager.
4590 In Qt, session management requests for action are handled by the two
4591 virtual functions QApplication::commitData() and QApplication::saveState().
4592 Both provide a reference to a session manager object as argument, to allow
4593 the application to communicate with the session manager. The session
4594 manager can only be accessed through these functions.
4595
4596 No user interaction is possible \e unless the application gets explicit
4597 permission from the session manager. You ask for permission by calling
4598 allowsInteraction() or, if it is really urgent, allowsErrorInteraction().
4599 Qt does not enforce this, but the session manager may.
4600
4601 You can try to abort the shutdown process by calling cancel(). The default
4602 commitData() function does this if some top-level window rejected its
4603 closeEvent().
4604
4605 For sophisticated session managers provided on Unix/X11, QSessionManager
4606 offers further possibilities to fine-tune an application's session
4607 management behavior: setRestartCommand(), setDiscardCommand(),
4608 setRestartHint(), setProperty(), requestPhase2(). See the respective
4609 function descriptions for further details.
4610
4611 \sa QApplication, {Session Management}
4612*/
4613
4614/*! \enum QSessionManager::RestartHint
4615
4616 This enum type defines the circumstances under which this application wants
4617 to be restarted by the session manager. The current values are:
4618
4619 \value RestartIfRunning If the application is still running when the
4620 session is shut down, it wants to be restarted
4621 at the start of the next session.
4622
4623 \value RestartAnyway The application wants to be started at the
4624 start of the next session, no matter what.
4625 (This is useful for utilities that run just
4626 after startup and then quit.)
4627
4628 \value RestartImmediately The application wants to be started immediately
4629 whenever it is not running.
4630
4631 \value RestartNever The application does not want to be restarted
4632 automatically.
4633
4634 The default hint is \c RestartIfRunning.
4635*/
4636
4637
4638/*!
4639 \fn QString QSessionManager::sessionId() const
4640
4641 Returns the identifier of the current session.
4642
4643 If the application has been restored from an earlier session, this
4644 identifier is the same as it was in the earlier session.
4645
4646 \sa sessionKey(), QApplication::sessionId()
4647*/
4648
4649/*!
4650 \fn QString QSessionManager::sessionKey() const
4651
4652 Returns the session key in the current session.
4653
4654 If the application has been restored from an earlier session, this key is
4655 the same as it was when the previous session ended.
4656
4657 The session key changes with every call of commitData() or saveState().
4658
4659 \sa sessionId(), QApplication::sessionKey()
4660*/
4661
4662/*!
4663 \fn void* QSessionManager::handle() const
4664
4665 \internal
4666*/
4667
4668/*!
4669 \fn bool QSessionManager::allowsInteraction()
4670
4671 Asks the session manager for permission to interact with the user. Returns
4672 true if interaction is permitted; otherwise returns false.
4673
4674 The rationale behind this mechanism is to make it possible to synchronize
4675 user interaction during a shutdown. Advanced session managers may ask all
4676 applications simultaneously to commit their data, resulting in a much
4677 faster shutdown.
4678
4679 When the interaction is completed we strongly recommend releasing the user
4680 interaction semaphore with a call to release(). This way, other
4681 applications may get the chance to interact with the user while your
4682 application is still busy saving data. (The semaphore is implicitly
4683 released when the application exits.)
4684
4685 If the user decides to cancel the shutdown process during the interaction
4686 phase, you must tell the session manager that this has happened by calling
4687 cancel().
4688
4689 Here's an example of how an application's QApplication::commitData() might
4690 be implemented:
4691
4692 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 8
4693
4694 If an error occurred within the application while saving its data, you may
4695 want to try allowsErrorInteraction() instead.
4696
4697 \sa QApplication::commitData(), release(), cancel()
4698*/
4699
4700
4701/*!
4702 \fn bool QSessionManager::allowsErrorInteraction()
4703
4704 Returns true if error interaction is permitted; otherwise returns false.
4705
4706 This is similar to allowsInteraction(), but also enables the application to
4707 tell the user about any errors that occur. Session managers may give error
4708 interaction requests higher priority, which means that it is more likely
4709 that an error interaction is permitted. However, you are still not
4710 guaranteed that the session manager will allow interaction.
4711
4712 \sa allowsInteraction(), release(), cancel()
4713*/
4714
4715/*!
4716 \fn void QSessionManager::release()
4717
4718 Releases the session manager's interaction semaphore after an interaction
4719 phase.
4720
4721 \sa allowsInteraction(), allowsErrorInteraction()
4722*/
4723
4724/*!
4725 \fn void QSessionManager::cancel()
4726
4727 Tells the session manager to cancel the shutdown process. Applications
4728 should not call this function without asking the user first.
4729
4730 \sa allowsInteraction(), allowsErrorInteraction()
4731*/
4732
4733/*!
4734 \fn void QSessionManager::setRestartHint(RestartHint hint)
4735
4736 Sets the application's restart hint to \a hint. On application startup, the
4737 hint is set to \c RestartIfRunning.
4738
4739 \note These flags are only hints, a session manager may or may not respect
4740 them.
4741
4742 We recommend setting the restart hint in QApplication::saveState() because
4743 most session managers perform a checkpoint shortly after an application's
4744 startup.
4745
4746 \sa restartHint()
4747*/
4748
4749/*!
4750 \fn QSessionManager::RestartHint QSessionManager::restartHint() const
4751
4752 Returns the application's current restart hint. The default is
4753 \c RestartIfRunning.
4754
4755 \sa setRestartHint()
4756*/
4757
4758/*!
4759 \fn void QSessionManager::setRestartCommand(const QStringList& command)
4760
4761 If the session manager is capable of restoring sessions it will execute
4762 \a command in order to restore the application. The command defaults to
4763
4764 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 9
4765
4766 The \c -session option is mandatory; otherwise QApplication cannot tell
4767 whether it has been restored or what the current session identifier is.
4768 See QApplication::isSessionRestored() and QApplication::sessionId() for
4769 details.
4770
4771 If your application is very simple, it may be possible to store the entire
4772 application state in additional command line options. This is usually a
4773 very bad idea because command lines are often limited to a few hundred
4774 bytes. Instead, use QSettings, temporary files, or a database for this
4775 purpose. By marking the data with the unique sessionId(), you will be able
4776 to restore the application in a future session.
4777
4778 \sa restartCommand(), setDiscardCommand(), setRestartHint()
4779*/
4780
4781/*!
4782 \fn QStringList QSessionManager::restartCommand() const
4783
4784 Returns the currently set restart command.
4785
4786 To iterate over the list, you can use the \l foreach pseudo-keyword:
4787
4788 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 10
4789
4790 \sa setRestartCommand(), restartHint()
4791*/
4792
4793/*!
4794 \fn void QSessionManager::setDiscardCommand(const QStringList& list)
4795
4796 Sets the discard command to the given \a list.
4797
4798 \sa discardCommand(), setRestartCommand()
4799*/
4800
4801
4802/*!
4803 \fn QStringList QSessionManager::discardCommand() const
4804
4805 Returns the currently set discard command.
4806
4807 To iterate over the list, you can use the \l foreach pseudo-keyword:
4808
4809 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 11
4810
4811 \sa setDiscardCommand(), restartCommand(), setRestartCommand()
4812*/
4813
4814/*!
4815 \fn void QSessionManager::setManagerProperty(const QString &name, const QString &value)
4816 \overload
4817
4818 Low-level write access to the application's identification and state
4819 records are kept in the session manager.
4820
4821 The property called \a name has its value set to the string \a value.
4822*/
4823
4824/*!
4825 \fn void QSessionManager::setManagerProperty(const QString& name,
4826 const QStringList& value)
4827
4828 Low-level write access to the application's identification and state record
4829 are kept in the session manager.
4830
4831 The property called \a name has its value set to the string list \a value.
4832*/
4833
4834/*!
4835 \fn bool QSessionManager::isPhase2() const
4836
4837 Returns true if the session manager is currently performing a second
4838 session management phase; otherwise returns false.
4839
4840 \sa requestPhase2()
4841*/
4842
4843/*!
4844 \fn void QSessionManager::requestPhase2()
4845
4846 Requests a second session management phase for the application. The
4847 application may then return immediately from the QApplication::commitData()
4848 or QApplication::saveState() function, and they will be called again once
4849 most or all other applications have finished their session management.
4850
4851 The two phases are useful for applications such as the X11 window manager
4852 that need to store information about another application's windows and
4853 therefore have to wait until these applications have completed their
4854 respective session management tasks.
4855
4856 \note If another application has requested a second phase it may get called
4857 before, simultaneously with, or after your application's second phase.
4858
4859 \sa isPhase2()
4860*/
4861
4862/*****************************************************************************
4863 Stubbed session management support
4864 *****************************************************************************/
4865#ifndef QT_NO_SESSIONMANAGER
4866#if defined(Q_WS_WIN) || defined(Q_WS_MAC) || defined(Q_WS_QWS)
4867
4868#if defined(Q_OS_WINCE)
4869HRESULT qt_CoCreateGuid(GUID* guid)
4870{
4871 // We will use the following information to create the GUID
4872 // 1. absolute path to application
4873 wchar_t tempFilename[MAX_PATH];
4874 if (!GetModuleFileName(0, tempFilename, MAX_PATH))
4875 return S_FALSE;
4876 unsigned int hash = qHash(QString::fromWCharArray(tempFilename));
4877 guid->Data1 = hash;
4878 // 2. creation time of file
4879 QFileInfo info(QString::fromWCharArray(tempFilename));
4880 guid->Data2 = qHash(info.created().toTime_t());
4881 // 3. current system time
4882 guid->Data3 = qHash(QDateTime::currentDateTime().toTime_t());
4883 return S_OK;
4884}
4885#if !defined(OLE32_MCOMGUID) || defined(QT_WINCE_FORCE_CREATE_GUID)
4886#define CoCreateGuid qt_CoCreateGuid
4887#endif
4888
4889#endif
4890
4891class QSessionManagerPrivate : public QObjectPrivate
4892{
4893public:
4894 QStringList restartCommand;
4895 QStringList discardCommand;
4896 QString sessionId;
4897 QString sessionKey;
4898 QSessionManager::RestartHint restartHint;
4899};
4900
4901QSessionManager* qt_session_manager_self = 0;
4902QSessionManager::QSessionManager(QApplication * app, QString &id, QString &key)
4903 : QObject(*new QSessionManagerPrivate, app)
4904{
4905 Q_D(QSessionManager);
4906 setObjectName(QLatin1String("qt_sessionmanager"));
4907 qt_session_manager_self = this;
4908#if defined(Q_WS_WIN)
4909 wchar_t guidstr[40];
4910 GUID guid;
4911 CoCreateGuid(&guid);
4912 StringFromGUID2(guid, guidstr, 40);
4913 id = QString::fromWCharArray(guidstr);
4914 CoCreateGuid(&guid);
4915 StringFromGUID2(guid, guidstr, 40);
4916 key = QString::fromWCharArray(guidstr);
4917#endif
4918 d->sessionId = id;
4919 d->sessionKey = key;
4920 d->restartHint = RestartIfRunning;
4921}
4922
4923QSessionManager::~QSessionManager()
4924{
4925 qt_session_manager_self = 0;
4926}
4927
4928QString QSessionManager::sessionId() const
4929{
4930 Q_D(const QSessionManager);
4931 return d->sessionId;
4932}
4933
4934QString QSessionManager::sessionKey() const
4935{
4936 Q_D(const QSessionManager);
4937 return d->sessionKey;
4938}
4939
4940
4941#if defined(Q_WS_X11) || defined(Q_WS_MAC)
4942void* QSessionManager::handle() const
4943{
4944 return 0;
4945}
4946#endif
4947
4948#if !defined(Q_WS_WIN)
4949bool QSessionManager::allowsInteraction()
4950{
4951 return true;
4952}
4953
4954bool QSessionManager::allowsErrorInteraction()
4955{
4956 return true;
4957}
4958void QSessionManager::release()
4959{
4960}
4961
4962void QSessionManager::cancel()
4963{
4964}
4965#endif
4966
4967
4968void QSessionManager::setRestartHint(QSessionManager::RestartHint hint)
4969{
4970 Q_D(QSessionManager);
4971 d->restartHint = hint;
4972}
4973
4974QSessionManager::RestartHint QSessionManager::restartHint() const
4975{
4976 Q_D(const QSessionManager);
4977 return d->restartHint;
4978}
4979
4980void QSessionManager::setRestartCommand(const QStringList& command)
4981{
4982 Q_D(QSessionManager);
4983 d->restartCommand = command;
4984}
4985
4986QStringList QSessionManager::restartCommand() const
4987{
4988 Q_D(const QSessionManager);
4989 return d->restartCommand;
4990}
4991
4992void QSessionManager::setDiscardCommand(const QStringList& command)
4993{
4994 Q_D(QSessionManager);
4995 d->discardCommand = command;
4996}
4997
4998QStringList QSessionManager::discardCommand() const
4999{
5000 Q_D(const QSessionManager);
5001 return d->discardCommand;
5002}
5003
5004void QSessionManager::setManagerProperty(const QString&, const QString&)
5005{
5006}
5007
5008void QSessionManager::setManagerProperty(const QString&, const QStringList&)
5009{
5010}
5011
5012bool QSessionManager::isPhase2() const
5013{
5014 return false;
5015}
5016
5017void QSessionManager::requestPhase2()
5018{
5019}
5020
5021#endif
5022#endif // QT_NO_SESSIONMANAGER
5023
5024/*!
5025 \typedef QApplication::ColorMode
5026 \compat
5027
5028 Use ColorSpec instead.
5029*/
5030
5031/*!
5032 \fn Qt::MacintoshVersion QApplication::macVersion()
5033
5034 Use QSysInfo::MacintoshVersion instead.
5035*/
5036
5037/*!
5038 \fn QApplication::ColorMode QApplication::colorMode()
5039
5040 Use colorSpec() instead, and use ColorSpec as the enum type.
5041*/
5042
5043/*!
5044 \fn void QApplication::setColorMode(ColorMode mode)
5045
5046 Use setColorSpec() instead, and pass a ColorSpec value instead.
5047*/
5048
5049/*!
5050 \fn bool QApplication::hasGlobalMouseTracking()
5051
5052 This feature does not exist anymore. This function always returns true
5053 in Qt 4.
5054*/
5055
5056/*!
5057 \fn void QApplication::setGlobalMouseTracking(bool dummy)
5058
5059 This function does nothing in Qt 4. The \a dummy parameter is ignored.
5060*/
5061
5062/*!
5063 \fn void QApplication::flushX()
5064
5065 Use flush() instead.
5066*/
5067
5068/*!
5069 \fn void QApplication::setWinStyleHighlightColor(const QColor &c)
5070
5071 Use the palette instead.
5072
5073 \oldcode
5074 app.setWinStyleHighlightColor(color);
5075 \newcode
5076 QPalette palette(QApplication::palette());
5077 palette.setColor(QPalette::Highlight, color);
5078 QApplication::setPalette(palette);
5079 \endcode
5080*/
5081
5082/*!
5083 \fn void QApplication::setPalette(const QPalette &pal, bool b, const char* className = 0)
5084
5085 Use the two-argument overload instead.
5086*/
5087
5088/*!
5089 \fn void QApplication::setFont(const QFont &font, bool b, const char* className = 0)
5090
5091 Use the two-argument overload instead.
5092*/
5093
5094/*!
5095 \fn const QColor &QApplication::winStyleHighlightColor()
5096
5097 Use QApplication::palette().color(QPalette::Active, QPalette::Highlight) instead.
5098*/
5099
5100/*!
5101 \fn QWidget *QApplication::widgetAt(int x, int y, bool child)
5102
5103 Use the two-argument widgetAt() overload to get the child widget. To get
5104 the top-level widget do this:
5105
5106 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 12
5107*/
5108
5109/*!
5110 \fn QWidget *QApplication::widgetAt(const QPoint &point, bool child)
5111
5112 Use the single-argument widgetAt() overload to get the child widget. To get
5113 the top-level widget do this:
5114
5115 \snippet doc/src/snippets/code/src_gui_kernel_qapplication.cpp 13
5116*/
5117
5118#ifdef QT3_SUPPORT
5119QWidget *QApplication::mainWidget()
5120{
5121 return QApplicationPrivate::main_widget;
5122}
5123#endif
5124bool QApplicationPrivate::inPopupMode() const
5125{
5126 return QApplicationPrivate::popupWidgets != 0;
5127}
5128
5129/*!
5130 \property QApplication::quitOnLastWindowClosed
5131
5132 \brief whether the application implicitly quits when the last window is
5133 closed.
5134
5135 The default is true.
5136
5137 If this property is true, the applications quits when the last visible
5138 primary window (i.e. window with no parent) with the Qt::WA_QuitOnClose
5139 attribute set is closed. By default this attribute is set for all widgets
5140 except for sub-windows. Refer to \l{Qt::WindowType} for a detailed list of
5141 Qt::Window objects.
5142
5143 \sa quit(), QWidget::close()
5144 */
5145
5146void QApplication::setQuitOnLastWindowClosed(bool quit)
5147{
5148 QApplicationPrivate::quitOnLastWindowClosed = quit;
5149}
5150
5151bool QApplication::quitOnLastWindowClosed()
5152{
5153 return QApplicationPrivate::quitOnLastWindowClosed;
5154}
5155
5156void QApplicationPrivate::emitLastWindowClosed()
5157{
5158 if (qApp && qApp->d_func()->in_exec) {
5159 if (QApplicationPrivate::quitOnLastWindowClosed) {
5160 // get ready to quit, this event might be removed if the
5161 // event loop is re-entered, however
5162 QApplication::postEvent(qApp, new QEvent(QEvent::Quit));
5163 }
5164 emit qApp->lastWindowClosed();
5165 }
5166}
5167
5168/*! \variable QApplication::NormalColors
5169 \compat
5170
5171 Use \l NormalColor instead.
5172*/
5173
5174/*! \variable QApplication::CustomColors
5175 \compat
5176
5177 Use \l CustomColor instead.
5178*/
5179
5180#ifdef QT_KEYPAD_NAVIGATION
5181/*!
5182 Sets the kind of focus navigation Qt should use to \a mode.
5183
5184 This feature is available in Qt for Embedded Linux, Symbian and Windows CE
5185 only.
5186
5187 \note On Windows CE this feature is disabled by default for touch device
5188 mkspecs. To enable keypad navigation, build Qt with
5189 QT_KEYPAD_NAVIGATION defined.
5190
5191 \note On Symbian, setting the mode to Qt::NavigationModeCursorAuto will enable a
5192 virtual mouse cursor on non touchscreen devices, which is controlled
5193 by the cursor keys if there is no analog pointer device.
5194 On other platforms and on touchscreen devices, it has the same
5195 meaning as Qt::NavigationModeNone.
5196
5197 \since 4.6
5198
5199 \sa keypadNavigationEnabled()
5200*/
5201void QApplication::setNavigationMode(Qt::NavigationMode mode)
5202{
5203#ifdef Q_OS_SYMBIAN
5204 QApplicationPrivate::setNavigationMode(mode);
5205#else
5206 QApplicationPrivate::navigationMode = mode;
5207#endif
5208}
5209
5210/*!
5211 Returns what kind of focus navigation Qt is using.
5212
5213 This feature is available in Qt for Embedded Linux, Symbian and Windows CE
5214 only.
5215
5216 \note On Windows CE this feature is disabled by default for touch device
5217 mkspecs. To enable keypad navigation, build Qt with
5218 QT_KEYPAD_NAVIGATION defined.
5219
5220 \note On Symbian, the default mode is Qt::NavigationModeNone for touch
5221 devices, and Qt::NavigationModeKeypadDirectional.
5222
5223 \since 4.6
5224
5225 \sa keypadNavigationEnabled()
5226*/
5227Qt::NavigationMode QApplication::navigationMode()
5228{
5229 return QApplicationPrivate::navigationMode;
5230}
5231
5232/*!
5233 Sets whether Qt should use focus navigation suitable for use with a
5234 minimal keypad.
5235
5236 This feature is available in Qt for Embedded Linux, Symbian and Windows CE
5237 only.
5238
5239 \note On Windows CE this feature is disabled by default for touch device
5240 mkspecs. To enable keypad navigation, build Qt with
5241 QT_KEYPAD_NAVIGATION defined.
5242
5243 \deprecated
5244
5245 \sa setNavigationMode()
5246*/
5247void QApplication::setKeypadNavigationEnabled(bool enable)
5248{
5249 if (enable) {
5250#ifdef Q_OS_SYMBIAN
5251 QApplication::setNavigationMode(Qt::NavigationModeKeypadDirectional);
5252#else
5253 QApplication::setNavigationMode(Qt::NavigationModeKeypadTabOrder);
5254#endif
5255 }
5256 else {
5257 QApplication::setNavigationMode(Qt::NavigationModeNone);
5258 }
5259}
5260
5261/*!
5262 Returns true if Qt is set to use keypad navigation; otherwise returns
5263 false. The default value is true on Symbian, but false on other platforms.
5264
5265 This feature is available in Qt for Embedded Linux, Symbian and Windows CE
5266 only.
5267
5268 \note On Windows CE this feature is disabled by default for touch device
5269 mkspecs. To enable keypad navigation, build Qt with
5270 QT_KEYPAD_NAVIGATION defined.
5271
5272 \deprecated
5273
5274 \sa navigationMode()
5275*/
5276bool QApplication::keypadNavigationEnabled()
5277{
5278 return QApplicationPrivate::navigationMode == Qt::NavigationModeKeypadTabOrder ||
5279 QApplicationPrivate::navigationMode == Qt::NavigationModeKeypadDirectional;
5280}
5281#endif
5282
5283/*!
5284 \fn void QApplication::alert(QWidget *widget, int msec)
5285 \since 4.3
5286
5287 Causes an alert to be shown for \a widget if the window is not the active
5288 window. The alert is shown for \a msec miliseconds. If \a msec is zero (the
5289 default), then the alert is shown indefinitely until the window becomes
5290 active again.
5291
5292 Currently this function does nothing on Qt for Embedded Linux.
5293
5294 On Mac OS X, this works more at the application level and will cause the
5295 application icon to bounce in the dock.
5296
5297 On Windows, this causes the window's taskbar entry to flash for a time. If
5298 \a msec is zero, the flashing will stop and the taskbar entry will turn a
5299 different color (currently orange).
5300
5301 On X11, this will cause the window to be marked as "demands attention", the
5302 window must not be hidden (i.e. not have hide() called on it, but be
5303 visible in some sort of way) in order for this to work.
5304*/
5305
5306/*!
5307 \property QApplication::cursorFlashTime
5308 \brief the text cursor's flash (blink) time in milliseconds
5309
5310 The flash time is the time required to display, invert and restore the
5311 caret display. Usually the text cursor is displayed for half the cursor
5312 flash time, then hidden for the same amount of time, but this may vary.
5313
5314 The default value on X11 is 1000 milliseconds. On Windows, the
5315 \gui{Control Panel} value is used and setting this property sets the cursor
5316 flash time for all applications.
5317
5318 We recommend that widgets do not cache this value as it may change at any
5319 time if the user changes the global desktop settings.
5320*/
5321
5322/*!
5323 \property QApplication::doubleClickInterval
5324 \brief the time limit in milliseconds that distinguishes a double click
5325 from two consecutive mouse clicks
5326
5327 The default value on X11 is 400 milliseconds. On Windows and Mac OS, the
5328 operating system's value is used. However, on Windows and Symbian OS,
5329 calling this function sets the double click interval for all applications.
5330*/
5331
5332/*!
5333 \property QApplication::keyboardInputInterval
5334 \brief the time limit in milliseconds that distinguishes a key press
5335 from two consecutive key presses
5336 \since 4.2
5337
5338 The default value on X11 is 400 milliseconds. On Windows and Mac OS, the
5339 operating system's value is used.
5340*/
5341
5342/*!
5343 \property QApplication::wheelScrollLines
5344 \brief the number of lines to scroll a widget, when the
5345 mouse wheel is rotated.
5346
5347 If the value exceeds the widget's number of visible lines, the widget
5348 should interpret the scroll operation as a single \e{page up} or
5349 \e{page down}. If the widget is an \l{QAbstractItemView}{item view class},
5350 then the result of scrolling one \e line depends on the setting of the
5351 widget's \l{QAbstractItemView::verticalScrollMode()}{scroll mode}. Scroll
5352 one \e line can mean \l{QAbstractItemView::ScrollPerItem}{scroll one item}
5353 or \l{QAbstractItemView::ScrollPerPixel}{scroll one pixel}.
5354
5355 By default, this property has a value of 3.
5356*/
5357
5358/*!
5359 \fn void QApplication::setEffectEnabled(Qt::UIEffect effect, bool enable)
5360
5361 Enables the UI effect \a effect if \a enable is true, otherwise the effect
5362 will not be used.
5363
5364 \note All effects are disabled on screens running at less than 16-bit color
5365 depth.
5366
5367 \sa isEffectEnabled(), Qt::UIEffect, setDesktopSettingsAware()
5368*/
5369
5370/*!
5371 \fn bool QApplication::isEffectEnabled(Qt::UIEffect effect)
5372
5373 Returns true if \a effect is enabled; otherwise returns false.
5374
5375 By default, Qt will try to use the desktop settings. To prevent this, call
5376 setDesktopSettingsAware(false).
5377
5378 \note All effects are disabled on screens running at less than 16-bit color
5379 depth.
5380
5381 \sa setEffectEnabled(), Qt::UIEffect
5382*/
5383
5384/*!
5385 \fn QWidget *QApplication::mainWidget()
5386
5387 Returns the main application widget, or 0 if there is no main widget.
5388*/
5389
5390/*!
5391 \fn void QApplication::setMainWidget(QWidget *mainWidget)
5392
5393 Sets the application's main widget to \a mainWidget.
5394
5395 In most respects the main widget is like any other widget, except that if
5396 it is closed, the application exits. QApplication does \e not take
5397 ownership of the \a mainWidget, so if you create your main widget on the
5398 heap you must delete it yourself.
5399
5400 You need not have a main widget; connecting lastWindowClosed() to quit()
5401 is an alternative.
5402
5403 On X11, this function also resizes and moves the main widget according
5404 to the \e -geometry command-line option, so you should set the default
5405 geometry (using \l QWidget::setGeometry()) before calling setMainWidget().
5406
5407 \sa mainWidget(), exec(), quit()
5408*/
5409
5410/*!
5411 \fn void QApplication::beep()
5412
5413 Sounds the bell, using the default volume and sound. The function is \e not
5414 available in Qt for Embedded Linux.
5415*/
5416
5417/*!
5418 \fn void QApplication::setOverrideCursor(const QCursor &cursor)
5419
5420 Sets the application override cursor to \a cursor.
5421
5422 Application override cursors are intended for showing the user that the
5423 application is in a special state, for example during an operation that
5424 might take some time.
5425
5426 This cursor will be displayed in all the application's widgets until
5427 restoreOverrideCursor() or another setOverrideCursor() is called.
5428
5429 Application cursors are stored on an internal stack. setOverrideCursor()
5430 pushes the cursor onto the stack, and restoreOverrideCursor() pops the
5431 active cursor off the stack. changeOverrideCursor() changes the curently
5432 active application override cursor.
5433
5434 Every setOverrideCursor() must eventually be followed by a corresponding
5435 restoreOverrideCursor(), otherwise the stack will never be emptied.
5436
5437 Example:
5438 \snippet doc/src/snippets/code/src_gui_kernel_qapplication_x11.cpp 0
5439
5440 \sa overrideCursor(), restoreOverrideCursor(), changeOverrideCursor(),
5441 QWidget::setCursor()
5442*/
5443
5444/*!
5445 \fn void QApplication::restoreOverrideCursor()
5446
5447 Undoes the last setOverrideCursor().
5448
5449 If setOverrideCursor() has been called twice, calling
5450 restoreOverrideCursor() will activate the first cursor set. Calling this
5451 function a second time restores the original widgets' cursors.
5452
5453 \sa setOverrideCursor(), overrideCursor()
5454*/
5455
5456/*!
5457 \macro qApp
5458 \relates QApplication
5459
5460 A global pointer referring to the unique application object. It is
5461 equivalent to the pointer returned by the QCoreApplication::instance()
5462 function except that, in GUI applications, it is a pointer to a
5463 QApplication instance.
5464
5465 Only one application object can be created.
5466
5467 \sa QCoreApplication::instance()
5468*/
5469
5470#ifndef QT_NO_IM
5471// ************************************************************************
5472// Input Method support
5473// ************************************************************************
5474
5475/*!
5476 This function replaces the QInputContext instance used by the application
5477 with \a inputContext.
5478
5479 Qt takes ownership of the given \a inputContext.
5480
5481 \sa inputContext()
5482*/
5483void QApplication::setInputContext(QInputContext *inputContext)
5484{
5485 if (inputContext == QApplicationPrivate::inputContext)
5486 return;
5487 if (!inputContext) {
5488 qWarning("QApplication::setInputContext: called with 0 input context");
5489 return;
5490 }
5491 delete QApplicationPrivate::inputContext;
5492 QApplicationPrivate::inputContext = inputContext;
5493 QApplicationPrivate::inputContext->setParent(this);
5494}
5495
5496/*!
5497 Returns the QInputContext instance used by the application.
5498
5499 \sa setInputContext()
5500*/
5501QInputContext *QApplication::inputContext() const
5502{
5503 Q_D(const QApplication);
5504 Q_UNUSED(d);// only static members being used.
5505 if (QApplicationPrivate::is_app_closing)
5506 return d->inputContext;
5507#ifdef Q_WS_X11
5508 if (!X11)
5509 return 0;
5510 if (!d->inputContext) {
5511 QApplication *that = const_cast<QApplication *>(this);
5512 QInputContext *qic = QInputContextFactory::create(X11->default_im, that);
5513 // fallback to default X Input Method.
5514 if (!qic)
5515 qic = QInputContextFactory::create(QLatin1String("xim"), that);
5516 that->d_func()->inputContext = qic;
5517 }
5518#elif defined(Q_OS_SYMBIAN)
5519 if (!d->inputContext) {
5520 QApplication *that = const_cast<QApplication *>(this);
5521 const QStringList keys = QInputContextFactory::keys();
5522 // Try hbim and coefep first, then try others.
5523 if (keys.contains(QLatin1String("hbim"))) {
5524 that->d_func()->inputContext = QInputContextFactory::create(QLatin1String("hbim"), that);
5525 } else if (keys.contains(QLatin1String("coefep"))) {
5526 if (!that->d_func()->inputContextBeingCreated) {
5527 that->d_func()->inputContextBeingCreated = true;
5528 that->d_func()->inputContext = QInputContextFactory::create(QLatin1String("coefep"), that);
5529 that->d_func()->inputContextBeingCreated = false;
5530 }
5531 } else {
5532 for (int c = 0; c < keys.size() && !d->inputContext; ++c) {
5533 that->d_func()->inputContext = QInputContextFactory::create(keys[c], that);
5534 }
5535 }
5536 }
5537#endif
5538 return d->inputContext;
5539}
5540#endif // QT_NO_IM
5541
5542//Returns the current platform used by keyBindings
5543uint QApplicationPrivate::currentPlatform(){
5544 uint platform = KB_Win;
5545#ifdef Q_WS_MAC
5546 platform = KB_Mac;
5547#elif defined Q_WS_X11
5548 platform = KB_X11;
5549 if (X11->desktopEnvironment == DE_KDE)
5550 platform |= KB_KDE;
5551 if (X11->desktopEnvironment == DE_GNOME)
5552 platform |= KB_Gnome;
5553 if (X11->desktopEnvironment == DE_CDE)
5554 platform |= KB_CDE;
5555#elif defined(Q_OS_SYMBIAN)
5556 platform = KB_S60;
5557#endif
5558 return platform;
5559}
5560
5561bool qt_sendSpontaneousEvent(QObject *receiver, QEvent *event)
5562{
5563 return QCoreApplication::sendSpontaneousEvent(receiver, event);
5564}
5565
5566
5567/*!
5568 \since 4.2
5569
5570 Returns the current keyboard input locale.
5571*/
5572QLocale QApplication::keyboardInputLocale()
5573{
5574 if (!QApplicationPrivate::checkInstance("keyboardInputLocale"))
5575 return QLocale::c();
5576 return qt_keymapper_private()->keyboardInputLocale;
5577}
5578
5579/*!
5580 \since 4.2
5581
5582 Returns the current keyboard input direction.
5583*/
5584Qt::LayoutDirection QApplication::keyboardInputDirection()
5585{
5586 if (!QApplicationPrivate::checkInstance("keyboardInputDirection"))
5587 return Qt::LeftToRight;
5588 return qt_keymapper_private()->keyboardInputDirection;
5589}
5590
5591void QApplicationPrivate::giveFocusAccordingToFocusPolicy(QWidget *widget,
5592 Qt::FocusPolicy focusPolicy,
5593 Qt::FocusReason focusReason)
5594{
5595 QWidget *focusWidget = widget;
5596 while (focusWidget) {
5597 if (focusWidget->isEnabled()
5598 && QApplicationPrivate::shouldSetFocus(focusWidget, focusPolicy)) {
5599 focusWidget->setFocus(focusReason);
5600 break;
5601 }
5602 if (focusWidget->isWindow())
5603 break;
5604 focusWidget = focusWidget->parentWidget();
5605 }
5606}
5607
5608bool QApplicationPrivate::shouldSetFocus(QWidget *w, Qt::FocusPolicy policy)
5609{
5610 QWidget *f = w;
5611 while (f->d_func()->extra && f->d_func()->extra->focus_proxy)
5612 f = f->d_func()->extra->focus_proxy;
5613
5614 if ((w->focusPolicy() & policy) != policy)
5615 return false;
5616 if (w != f && (f->focusPolicy() & policy) != policy)
5617 return false;
5618 return true;
5619}
5620
5621/*! \fn QDecoration &QApplication::qwsDecoration()
5622 Return the QWSDecoration used for decorating windows.
5623
5624 \warning This method is non-portable. It is only available in
5625 Qt for Embedded Linux.
5626
5627 \sa QDecoration
5628*/
5629
5630/*!
5631 \fn void QApplication::qwsSetDecoration(QDecoration *decoration)
5632
5633 Sets the QDecoration derived class to use for decorating the
5634 windows used by Qt for Embedded Linux to the \a decoration
5635 specified.
5636
5637 This method is non-portable. It is only available in Qt for Embedded Linux.
5638
5639 \sa QDecoration
5640*/
5641
5642/*! \fn QDecoration* QApplication::qwsSetDecoration(const QString &decoration)
5643 \overload
5644
5645 Requests a QDecoration object for \a decoration from the
5646 QDecorationFactory.
5647
5648 The string must be one of the QDecorationFactory::keys(). Keys are case
5649 insensitive.
5650
5651 A later call to the QApplication constructor will override the requested
5652 style when a "-style" option is passed in as a commandline parameter.
5653
5654 Returns 0 if an unknown \a decoration is passed, otherwise the QStyle object
5655 returned is set as the application's GUI style.
5656*/
5657
5658/*!
5659 \fn bool QApplication::qwsEventFilter(QWSEvent *event)
5660
5661 This virtual function is only implemented under Qt for Embedded Linux.
5662
5663 If you create an application that inherits QApplication and
5664 reimplement this function, you get direct access to all QWS (Q
5665 Window System) events that the are received from the QWS master
5666 process. The events are passed in the \a event parameter.
5667
5668 Return true if you want to stop the event from being processed.
5669 Return false for normal event dispatching. The default
5670 implementation returns false.
5671*/
5672
5673/*! \fn void QApplication::qwsSetCustomColors(QRgb *colorTable, int start, int numColors)
5674 Set Qt for Embedded Linux custom color table.
5675
5676 Qt for Embedded Linux on 8-bpp displays allocates a standard 216 color cube.
5677 The remaining 40 colors may be used by setting a custom color
5678 table in the QWS master process before any clients connect.
5679
5680 \a colorTable is an array of up to 40 custom colors. \a start is
5681 the starting index (0-39) and \a numColors is the number of colors
5682 to be set (1-40).
5683
5684 This method is non-portable. It is available \e only in
5685 Qt for Embedded Linux.
5686
5687 \note The custom colors will not be used by the default screen
5688 driver. To make use of the new colors, implement a custom screen
5689 driver, or use QDirectPainter.
5690*/
5691
5692/*! \fn int QApplication::qwsProcessEvent(QWSEvent* event)
5693 \internal
5694*/
5695
5696/*! \fn int QApplication::x11ClientMessage(QWidget* w, XEvent* event, bool passive_only)
5697 \internal
5698*/
5699
5700/*! \fn int QApplication::x11ProcessEvent(XEvent* event)
5701 This function does the core processing of individual X
5702 \a{event}s, normally by dispatching Qt events to the right
5703 destination.
5704
5705 It returns 1 if the event was consumed by special handling, 0 if
5706 the \a event was consumed by normal handling, and -1 if the \a
5707 event was for an unrecognized widget.
5708
5709 \sa x11EventFilter()
5710*/
5711
5712/*!
5713 \fn bool QApplication::x11EventFilter(XEvent *event)
5714
5715 \warning This virtual function is only implemented under X11.
5716
5717 If you create an application that inherits QApplication and
5718 reimplement this function, you get direct access to all X events
5719 that the are received from the X server. The events are passed in
5720 the \a event parameter.
5721
5722 Return true if you want to stop the event from being processed.
5723 Return false for normal event dispatching. The default
5724 implementation returns false.
5725
5726 It is only the directly addressed messages that are filtered.
5727 You must install an event filter directly on the event
5728 dispatcher, which is returned by
5729 QAbstractEventDispatcher::instance(), to handle system wide
5730 messages.
5731
5732 \sa x11ProcessEvent()
5733*/
5734
5735/*! \fn void QApplication::winFocus(QWidget *widget, bool gotFocus)
5736 \internal
5737 \since 4.1
5738
5739 If \a gotFocus is true, \a widget will become the active window.
5740 Otherwise the active window is reset to 0.
5741*/
5742
5743/*! \fn void QApplication::winMouseButtonUp()
5744 \internal
5745 */
5746
5747/*! \fn void QApplication::syncX()
5748 Synchronizes with the X server in the X11 implementation.
5749 This normally takes some time. Does nothing on other platforms.
5750*/
5751
5752void QApplicationPrivate::updateTouchPointsForWidget(QWidget *widget, QTouchEvent *touchEvent)
5753{
5754 for (int i = 0; i < touchEvent->touchPoints().count(); ++i) {
5755 QTouchEvent::TouchPoint &touchPoint = touchEvent->_touchPoints[i];
5756
5757 // preserve the sub-pixel resolution
5758 QRectF rect = touchPoint.screenRect();
5759 const QPointF screenPos = rect.center();
5760 const QPointF delta = screenPos - screenPos.toPoint();
5761
5762 rect.moveCenter(widget->mapFromGlobal(screenPos.toPoint()) + delta);
5763 touchPoint.d->rect = rect;
5764 if (touchPoint.state() == Qt::TouchPointPressed) {
5765 touchPoint.d->startPos = widget->mapFromGlobal(touchPoint.startScreenPos().toPoint()) + delta;
5766 touchPoint.d->lastPos = widget->mapFromGlobal(touchPoint.lastScreenPos().toPoint()) + delta;
5767 }
5768 }
5769}
5770
5771void QApplicationPrivate::initializeMultitouch()
5772{
5773 widgetForTouchPointId.clear();
5774 appCurrentTouchPoints.clear();
5775
5776 initializeMultitouch_sys();
5777}
5778
5779void QApplicationPrivate::cleanupMultitouch()
5780{
5781 cleanupMultitouch_sys();
5782
5783 widgetForTouchPointId.clear();
5784 appCurrentTouchPoints.clear();
5785}
5786
5787int QApplicationPrivate::findClosestTouchPointId(const QPointF &screenPos)
5788{
5789 int closestTouchPointId = -1;
5790 qreal closestDistance = qreal(0.);
5791 foreach (const QTouchEvent::TouchPoint &touchPoint, appCurrentTouchPoints) {
5792 qreal distance = QLineF(screenPos, touchPoint.screenPos()).length();
5793 if (closestTouchPointId == -1 || distance < closestDistance) {
5794 closestTouchPointId = touchPoint.id();
5795 closestDistance = distance;
5796 }
5797 }
5798 return closestTouchPointId;
5799}
5800
5801void QApplicationPrivate::translateRawTouchEvent(QWidget *window,
5802 QTouchEvent::DeviceType deviceType,
5803 const QList<QTouchEvent::TouchPoint> &touchPoints)
5804{
5805 QApplicationPrivate *d = self;
5806 typedef QPair<Qt::TouchPointStates, QList<QTouchEvent::TouchPoint> > StatesAndTouchPoints;
5807 QHash<QWidget *, StatesAndTouchPoints> widgetsNeedingEvents;
5808
5809 for (int i = 0; i < touchPoints.count(); ++i) {
5810 QTouchEvent::TouchPoint touchPoint = touchPoints.at(i);
5811 // explicitly detach from the original touch point that we got, so even
5812 // if the touchpoint structs are reused, we will make a copy that we'll
5813 // deliver to the user (which might want to store the struct for later use).
5814 touchPoint.d = touchPoint.d->detach();
5815
5816 // update state
5817 QWeakPointer<QWidget> widget;
5818 switch (touchPoint.state()) {
5819 case Qt::TouchPointPressed:
5820 {
5821 if (deviceType == QTouchEvent::TouchPad) {
5822 // on touch-pads, send all touch points to the same widget
5823 widget = d->widgetForTouchPointId.isEmpty()
5824 ? QWeakPointer<QWidget>()
5825 : d->widgetForTouchPointId.constBegin().value();
5826 }
5827
5828 if (!widget) {
5829 // determine which widget this event will go to
5830 if (!window)
5831 window = QApplication::topLevelAt(touchPoint.screenPos().toPoint());
5832 if (!window)
5833 continue;
5834 widget = window->childAt(window->mapFromGlobal(touchPoint.screenPos().toPoint()));
5835 if (!widget)
5836 widget = window;
5837 }
5838
5839 if (deviceType == QTouchEvent::TouchScreen) {
5840 int closestTouchPointId = d->findClosestTouchPointId(touchPoint.screenPos());
5841 QWidget *closestWidget = d->widgetForTouchPointId.value(closestTouchPointId).data();
5842 if (closestWidget
5843 && (widget.data()->isAncestorOf(closestWidget) || closestWidget->isAncestorOf(widget.data()))) {
5844 widget = closestWidget;
5845 }
5846 }
5847
5848 d->widgetForTouchPointId[touchPoint.id()] = widget;
5849 touchPoint.d->startScreenPos = touchPoint.screenPos();
5850 touchPoint.d->lastScreenPos = touchPoint.screenPos();
5851 touchPoint.d->startNormalizedPos = touchPoint.normalizedPos();
5852 touchPoint.d->lastNormalizedPos = touchPoint.normalizedPos();
5853 if (touchPoint.pressure() < qreal(0.))
5854 touchPoint.d->pressure = qreal(1.);
5855
5856 d->appCurrentTouchPoints.insert(touchPoint.id(), touchPoint);
5857 break;
5858 }
5859 case Qt::TouchPointReleased:
5860 {
5861 widget = d->widgetForTouchPointId.take(touchPoint.id());
5862 if (!widget)
5863 continue;
5864
5865 QTouchEvent::TouchPoint previousTouchPoint = d->appCurrentTouchPoints.take(touchPoint.id());
5866 touchPoint.d->startScreenPos = previousTouchPoint.startScreenPos();
5867 touchPoint.d->lastScreenPos = previousTouchPoint.screenPos();
5868 touchPoint.d->startPos = previousTouchPoint.startPos();
5869 touchPoint.d->lastPos = previousTouchPoint.pos();
5870 touchPoint.d->startNormalizedPos = previousTouchPoint.startNormalizedPos();
5871 touchPoint.d->lastNormalizedPos = previousTouchPoint.normalizedPos();
5872 if (touchPoint.pressure() < qreal(0.))
5873 touchPoint.d->pressure = qreal(0.);
5874 break;
5875 }
5876 default:
5877 widget = d->widgetForTouchPointId.value(touchPoint.id());
5878 if (!widget)
5879 continue;
5880
5881 Q_ASSERT(d->appCurrentTouchPoints.contains(touchPoint.id()));
5882 QTouchEvent::TouchPoint previousTouchPoint = d->appCurrentTouchPoints.value(touchPoint.id());
5883 touchPoint.d->startScreenPos = previousTouchPoint.startScreenPos();
5884 touchPoint.d->lastScreenPos = previousTouchPoint.screenPos();
5885 touchPoint.d->startPos = previousTouchPoint.startPos();
5886 touchPoint.d->lastPos = previousTouchPoint.pos();
5887 touchPoint.d->startNormalizedPos = previousTouchPoint.startNormalizedPos();
5888 touchPoint.d->lastNormalizedPos = previousTouchPoint.normalizedPos();
5889 if (touchPoint.pressure() < qreal(0.))
5890 touchPoint.d->pressure = qreal(1.);
5891 d->appCurrentTouchPoints[touchPoint.id()] = touchPoint;
5892 break;
5893 }
5894 Q_ASSERT(widget.data() != 0);
5895
5896 // make the *scene* functions return the same as the *screen* functions
5897 touchPoint.d->sceneRect = touchPoint.screenRect();
5898 touchPoint.d->startScenePos = touchPoint.startScreenPos();
5899 touchPoint.d->lastScenePos = touchPoint.lastScreenPos();
5900
5901 StatesAndTouchPoints &maskAndPoints = widgetsNeedingEvents[widget.data()];
5902 maskAndPoints.first |= touchPoint.state();
5903 if (touchPoint.isPrimary())
5904 maskAndPoints.first |= Qt::TouchPointPrimary;
5905 maskAndPoints.second.append(touchPoint);
5906 }
5907
5908 if (widgetsNeedingEvents.isEmpty())
5909 return;
5910
5911 QHash<QWidget *, StatesAndTouchPoints>::ConstIterator it = widgetsNeedingEvents.constBegin();
5912 const QHash<QWidget *, StatesAndTouchPoints>::ConstIterator end = widgetsNeedingEvents.constEnd();
5913 for (; it != end; ++it) {
5914 QWidget *widget = it.key();
5915 if (!QApplicationPrivate::tryModalHelper(widget, 0))
5916 continue;
5917
5918 QEvent::Type eventType;
5919 switch (it.value().first & Qt::TouchPointStateMask) {
5920 case Qt::TouchPointPressed:
5921 eventType = QEvent::TouchBegin;
5922 break;
5923 case Qt::TouchPointReleased:
5924 eventType = QEvent::TouchEnd;
5925 break;
5926 case Qt::TouchPointStationary:
5927 // don't send the event if nothing changed
5928 continue;
5929 default:
5930 eventType = QEvent::TouchUpdate;
5931 break;
5932 }
5933
5934 QTouchEvent touchEvent(eventType,
5935 deviceType,
5936 QApplication::keyboardModifiers(),
5937 it.value().first,
5938 it.value().second);
5939 updateTouchPointsForWidget(widget, &touchEvent);
5940
5941 switch (touchEvent.type()) {
5942 case QEvent::TouchBegin:
5943 {
5944 // if the TouchBegin handler recurses, we assume that means the event
5945 // has been implicitly accepted and continue to send touch events
5946 widget->setAttribute(Qt::WA_WState_AcceptedTouchBeginEvent);
5947 (void ) QApplication::sendSpontaneousEvent(widget, &touchEvent);
5948 break;
5949 }
5950 default:
5951 if (widget->testAttribute(Qt::WA_WState_AcceptedTouchBeginEvent)) {
5952 if (touchEvent.type() == QEvent::TouchEnd)
5953 widget->setAttribute(Qt::WA_WState_AcceptedTouchBeginEvent, false);
5954 (void) QApplication::sendSpontaneousEvent(widget, &touchEvent);
5955 }
5956 break;
5957 }
5958 }
5959}
5960
5961Q_GUI_EXPORT void qt_translateRawTouchEvent(QWidget *window,
5962 QTouchEvent::DeviceType deviceType,
5963 const QList<QTouchEvent::TouchPoint> &touchPoints)
5964{
5965 QApplicationPrivate::translateRawTouchEvent(window, deviceType, touchPoints);
5966}
5967
5968#ifndef QT_NO_GESTURES
5969QGestureManager* QGestureManager::instance()
5970{
5971 QApplicationPrivate *qAppPriv = QApplicationPrivate::instance();
5972 if (!qAppPriv)
5973 return 0;
5974 if (!qAppPriv->gestureManager)
5975 qAppPriv->gestureManager = new QGestureManager(qApp);
5976 return qAppPriv->gestureManager;
5977}
5978#endif // QT_NO_GESTURES
5979
5980// These pixmaps approximate the images in the Windows User Interface Guidelines.
5981
5982// XPM
5983
5984static const char * const move_xpm[] = {
5985"11 20 3 1",
5986". c None",
5987#if defined(Q_WS_WIN)
5988"a c #000000",
5989"X c #FFFFFF", // Windows cursor is traditionally white
5990#else
5991"a c #FFFFFF",
5992"X c #000000", // X11 cursor is traditionally black
5993#endif
5994"aa.........",
5995"aXa........",
5996"aXXa.......",
5997"aXXXa......",
5998"aXXXXa.....",
5999"aXXXXXa....",
6000"aXXXXXXa...",
6001"aXXXXXXXa..",
6002"aXXXXXXXXa.",
6003"aXXXXXXXXXa",
6004"aXXXXXXaaaa",
6005"aXXXaXXa...",
6006"aXXaaXXa...",
6007"aXa..aXXa..",
6008"aa...aXXa..",
6009"a.....aXXa.",
6010"......aXXa.",
6011".......aXXa",
6012".......aXXa",
6013"........aa."};
6014
6015#ifdef Q_WS_WIN
6016/* XPM */
6017static const char * const ignore_xpm[] = {
6018"24 30 3 1",
6019". c None",
6020"a c #000000",
6021"X c #FFFFFF",
6022"aa......................",
6023"aXa.....................",
6024"aXXa....................",
6025"aXXXa...................",
6026"aXXXXa..................",
6027"aXXXXXa.................",
6028"aXXXXXXa................",
6029"aXXXXXXXa...............",
6030"aXXXXXXXXa..............",
6031"aXXXXXXXXXa.............",
6032"aXXXXXXaaaa.............",
6033"aXXXaXXa................",
6034"aXXaaXXa................",
6035"aXa..aXXa...............",
6036"aa...aXXa...............",
6037"a.....aXXa..............",
6038"......aXXa.....XXXX.....",
6039".......aXXa..XXaaaaXX...",
6040".......aXXa.XaaaaaaaaX..",
6041"........aa.XaaaXXXXaaaX.",
6042"...........XaaaaX..XaaX.",
6043"..........XaaXaaaX..XaaX",
6044"..........XaaXXaaaX.XaaX",
6045"..........XaaX.XaaaXXaaX",
6046"..........XaaX..XaaaXaaX",
6047"...........XaaX..XaaaaX.",
6048"...........XaaaXXXXaaaX.",
6049"............XaaaaaaaaX..",
6050".............XXaaaaXX...",
6051"...............XXXX....."};
6052#endif
6053
6054/* XPM */
6055static const char * const copy_xpm[] = {
6056"24 30 3 1",
6057". c None",
6058"a c #000000",
6059"X c #FFFFFF",
6060#if defined(Q_WS_WIN) // Windows cursor is traditionally white
6061"aa......................",
6062"aXa.....................",
6063"aXXa....................",
6064"aXXXa...................",
6065"aXXXXa..................",
6066"aXXXXXa.................",
6067"aXXXXXXa................",
6068"aXXXXXXXa...............",
6069"aXXXXXXXXa..............",
6070"aXXXXXXXXXa.............",
6071"aXXXXXXaaaa.............",
6072"aXXXaXXa................",
6073"aXXaaXXa................",
6074"aXa..aXXa...............",
6075"aa...aXXa...............",
6076"a.....aXXa..............",
6077"......aXXa..............",
6078".......aXXa.............",
6079".......aXXa.............",
6080"........aa...aaaaaaaaaaa",
6081#else
6082"XX......................",
6083"XaX.....................",
6084"XaaX....................",
6085"XaaaX...................",
6086"XaaaaX..................",
6087"XaaaaaX.................",
6088"XaaaaaaX................",
6089"XaaaaaaaX...............",
6090"XaaaaaaaaX..............",
6091"XaaaaaaaaaX.............",
6092"XaaaaaaXXXX.............",
6093"XaaaXaaX................",
6094"XaaXXaaX................",
6095"XaX..XaaX...............",
6096"XX...XaaX...............",
6097"X.....XaaX..............",
6098"......XaaX..............",
6099".......XaaX.............",
6100".......XaaX.............",
6101"........XX...aaaaaaaaaaa",
6102#endif
6103".............aXXXXXXXXXa",
6104".............aXXXXXXXXXa",
6105".............aXXXXaXXXXa",
6106".............aXXXXaXXXXa",
6107".............aXXaaaaaXXa",
6108".............aXXXXaXXXXa",
6109".............aXXXXaXXXXa",
6110".............aXXXXXXXXXa",
6111".............aXXXXXXXXXa",
6112".............aaaaaaaaaaa"};
6113
6114/* XPM */
6115static const char * const link_xpm[] = {
6116"24 30 3 1",
6117". c None",
6118"a c #000000",
6119"X c #FFFFFF",
6120#if defined(Q_WS_WIN) // Windows cursor is traditionally white
6121"aa......................",
6122"aXa.....................",
6123"aXXa....................",
6124"aXXXa...................",
6125"aXXXXa..................",
6126"aXXXXXa.................",
6127"aXXXXXXa................",
6128"aXXXXXXXa...............",
6129"aXXXXXXXXa..............",
6130"aXXXXXXXXXa.............",
6131"aXXXXXXaaaa.............",
6132"aXXXaXXa................",
6133"aXXaaXXa................",
6134"aXa..aXXa...............",
6135"aa...aXXa...............",
6136"a.....aXXa..............",
6137"......aXXa..............",
6138".......aXXa.............",
6139".......aXXa.............",
6140"........aa...aaaaaaaaaaa",
6141#else
6142"XX......................",
6143"XaX.....................",
6144"XaaX....................",
6145"XaaaX...................",
6146"XaaaaX..................",
6147"XaaaaaX.................",
6148"XaaaaaaX................",
6149"XaaaaaaaX...............",
6150"XaaaaaaaaX..............",
6151"XaaaaaaaaaX.............",
6152"XaaaaaaXXXX.............",
6153"XaaaXaaX................",
6154"XaaXXaaX................",
6155"XaX..XaaX...............",
6156"XX...XaaX...............",
6157"X.....XaaX..............",
6158"......XaaX..............",
6159".......XaaX.............",
6160".......XaaX.............",
6161"........XX...aaaaaaaaaaa",
6162#endif
6163".............aXXXXXXXXXa",
6164".............aXXXaaaaXXa",
6165".............aXXXXaaaXXa",
6166".............aXXXaaaaXXa",
6167".............aXXaaaXaXXa",
6168".............aXXaaXXXXXa",
6169".............aXXaXXXXXXa",
6170".............aXXXaXXXXXa",
6171".............aXXXXXXXXXa",
6172".............aaaaaaaaaaa"};
6173
6174QPixmap QApplicationPrivate::getPixmapCursor(Qt::CursorShape cshape)
6175{
6176#if defined(Q_WS_X11) || defined(Q_WS_WIN)
6177 if (!move_cursor) {
6178 move_cursor = new QPixmap((const char **)move_xpm);
6179 copy_cursor = new QPixmap((const char **)copy_xpm);
6180 link_cursor = new QPixmap((const char **)link_xpm);
6181#ifdef Q_WS_WIN
6182 ignore_cursor = new QPixmap((const char **)ignore_xpm);
6183#endif
6184 }
6185
6186 switch (cshape) {
6187 case Qt::DragMoveCursor:
6188 return *move_cursor;
6189 case Qt::DragCopyCursor:
6190 return *copy_cursor;
6191 case Qt::DragLinkCursor:
6192 return *link_cursor;
6193#ifdef Q_WS_WIN
6194 case Qt::ForbiddenCursor:
6195 return *ignore_cursor;
6196#endif
6197 default:
6198 break;
6199 }
6200#else
6201 Q_UNUSED(cshape);
6202#endif
6203 return QPixmap();
6204}
6205
6206QT_END_NAMESPACE
6207
6208#include "moc_qapplication.cpp"
6209