source: trunk/src/gui/kernel/qapplication.cpp@ 336

Last change on this file since 336 was 182, checked in by Dmitry A. Kuminov, 16 years ago

gui: Implemented standard cursor shapes (#54).

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