summaryrefslogtreecommitdiffstats
path: root/src/gui/kernel/qguiapplication.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/gui/kernel/qguiapplication.cpp')
-rw-r--r--src/gui/kernel/qguiapplication.cpp330
1 files changed, 283 insertions, 47 deletions
diff --git a/src/gui/kernel/qguiapplication.cpp b/src/gui/kernel/qguiapplication.cpp
index 7cb3d4b488..1cd448a6bb 100644
--- a/src/gui/kernel/qguiapplication.cpp
+++ b/src/gui/kernel/qguiapplication.cpp
@@ -99,6 +99,14 @@ QPlatformTheme *QGuiApplicationPrivate::platform_theme = 0;
QList<QObject *> QGuiApplicationPrivate::generic_plugin_list;
+enum ApplicationResourceFlags
+{
+ ApplicationPaletteExplicitlySet = 0x1,
+ ApplicationFontExplicitlySet = 0x2
+};
+
+static unsigned applicationResourceFlags = 0;
+
bool QGuiApplicationPrivate::app_do_modal = false;
QPalette *QGuiApplicationPrivate::app_pal = 0; // default application palette
@@ -144,7 +152,169 @@ static bool qt_detectRTLLanguage()
" and Arabic) to get proper widget layout.") == QLatin1String("RTL"));
}
+static void initPalette()
+{
+ if (!QGuiApplicationPrivate::app_pal)
+ if (const QPalette *themePalette = QGuiApplicationPrivate::platformTheme()->palette())
+ QGuiApplicationPrivate::app_pal = new QPalette(*themePalette);
+ if (!QGuiApplicationPrivate::app_pal)
+ QGuiApplicationPrivate::app_pal = new QPalette(Qt::black);
+}
+
+static inline void clearPalette()
+{
+ delete QGuiApplicationPrivate::app_pal;
+ QGuiApplicationPrivate::app_pal = 0;
+}
+
+static void initFontUnlocked()
+{
+ if (!QGuiApplicationPrivate::app_font)
+ QGuiApplicationPrivate::app_font =
+ new QFont(QGuiApplicationPrivate::platformIntegration()->fontDatabase()->defaultFont());
+}
+
+static inline void clearFontUnlocked()
+{
+ delete QGuiApplicationPrivate::app_font;
+ QGuiApplicationPrivate::app_font = 0;
+}
+
+/*!
+ \class QGuiApplication
+ \brief The QGuiApplication class manages the GUI application's control
+ flow and main settings.
+
+ \inmodule QtGui
+
+ QGuiApplication contains the main event loop, where all events from the window
+ system and other sources are processed and dispatched. It also handles the
+ application's initialization and finalization. In addition, QGuiApplication handles
+ most of the system-wide and application-wide settings.
+
+ For any GUI application using Qt, there is precisely \bold one QGuiApplication
+ object no matter whether the application has 0, 1, 2 or more windows at
+ any given time. For non-GUI Qt applications, use QCoreApplication instead,
+ as it does not depend on the \l QtGui library.
+
+ The QGuiApplication object is accessible through the instance() function, which
+ returns a pointer equivalent to the global \l qApp pointer.
+
+ QGuiApplication's main areas of responsibility are:
+ \list
+ \o It initializes the application with the user's desktop settings,
+ such as palette(), font() and styleHints(). It keeps
+ track of these properties in case the user changes the desktop
+ globally, for example, through some kind of control panel.
+
+ \o It performs event handling, meaning that it receives events
+ from the underlying window system and dispatches them to the
+ relevant widgets. You can send your own events to windows by
+ using sendEvent() and postEvent().
+
+ \o It parses common command line arguments and sets its internal
+ state accordingly. See the \l{QGuiApplication::QGuiApplication()}
+ {constructor documentation} below for more details.
+
+ \o It provides localization of strings that are visible to the
+ user via translate().
+
+ \o It provides some magical objects like the clipboard().
+
+ \o It knows about the application's windows. You can ask which
+ window is at a certain position using topLevelAt(), get a list of
+ topLevelWindows(), etc.
+
+ \o It manages the application's mouse cursor handling, see
+ setOverrideCursor()
+ \endlist
+
+ Since the QGuiApplication object does so much initialization, it \e{must} be
+ created before any other objects related to the user interface are created.
+ QGuiApplication also deals with common command line arguments. Hence, it is
+ usually a good idea to create it \e before any interpretation or
+ modification of \c argv is done in the application itself.
+
+ \table
+ \header
+ \o{2,1} Groups of functions
+
+ \row
+ \o System settings
+ \o desktopSettingsAware(),
+ setDesktopSettingsAware(),
+ styleHints(),
+ palette(),
+ setPalette(),
+ font(),
+ setFont().
+
+ \row
+ \o Event handling
+ \o exec(),
+ processEvents(),
+ exit(),
+ quit().
+ sendEvent(),
+ postEvent(),
+ sendPostedEvents(),
+ removePostedEvents(),
+ hasPendingEvents(),
+ notify().
+
+ \row
+ \o Windows
+ \o allWindows(),
+ topLevelWindows(),
+ focusWindow(),
+ clipboard(),
+ topLevelAt().
+
+ \row
+ \o Advanced cursor handling
+ \o overrideCursor(),
+ setOverrideCursor(),
+ restoreOverrideCursor().
+
+ \row
+ \o Miscellaneous
+ \o startingUp(),
+ closingDown(),
+ type().
+ \endtable
+
+ \sa QCoreApplication, QAbstractEventDispatcher, QEventLoop
+*/
+
+/*!
+ Initializes the window system and constructs an application object with
+ \a argc command line arguments in \a argv.
+
+ \warning The data referred to by \a argc and \a argv must stay valid for
+ the entire lifetime of the QGuiApplication object. In addition, \a argc must
+ be greater than zero and \a argv must contain at least one valid character
+ string.
+
+ The global \c qApp pointer refers to this application object. Only one
+ application object should be created.
+
+ This application object must be constructed before any \l{QPaintDevice}
+ {paint devices} (including pixmaps, bitmaps etc.).
+
+ \note \a argc and \a argv might be changed as Qt removes command line
+ arguments that it recognizes.
+ All Qt programs automatically support the following command line options:
+ \list
+ \o -reverse, sets the application's layout direction to
+ Qt::RightToLeft
+ \o -qmljsdebugger=, activates the QML/JS debugger with a specified port.
+ The value must be of format port:1234[,block], where block is optional
+ and will make the application wait until a debugger connects to it.
+ \endlist
+
+ \sa arguments()
+*/
QGuiApplication::QGuiApplication(int &argc, char **argv, int flags)
: QCoreApplication(*new QGuiApplicationPrivate(argc, argv, flags))
{
@@ -159,6 +329,9 @@ QGuiApplication::QGuiApplication(QGuiApplicationPrivate &p)
d_func()->init();
}
+/*!
+ Destructs the application.
+*/
QGuiApplication::~QGuiApplication()
{
Q_D(QGuiApplication);
@@ -174,8 +347,7 @@ QGuiApplication::~QGuiApplication()
delete QGuiApplicationPrivate::qt_clipboard;
QGuiApplicationPrivate::qt_clipboard = 0;
- delete QGuiApplicationPrivate::app_pal;
- QGuiApplicationPrivate::app_pal = 0;
+ clearPalette();
qUnregisterGuiVariant();
@@ -194,6 +366,10 @@ QGuiApplicationPrivate::QGuiApplicationPrivate(int &argc, char **argv, int flags
application_type = QCoreApplication::GuiClient;
}
+/*!
+ Returns the QWindow that receives events tied to focus,
+ such as key events.
+*/
QWindow *QGuiApplication::focusWindow()
{
return QGuiApplicationPrivate::focus_window;
@@ -208,7 +384,7 @@ QWindow *QGuiApplication::focusWindow()
/*!
Returns the QObject in currently active window that will be final receiver of events
- tied focus, such as key events.
+ tied to focus, such as key events.
*/
QObject *QGuiApplication::focusObject()
{
@@ -249,6 +425,11 @@ QWindowList QGuiApplication::topLevelWindows()
return topLevelWindows;
}
+/*!
+ Returns the primary (or default) screen of the application.
+
+ This will be the screen where QWindows are shown, unless otherwise specified.
+*/
QScreen *QGuiApplication::primaryScreen()
{
if (QGuiApplicationPrivate::screen_list.isEmpty())
@@ -256,11 +437,18 @@ QScreen *QGuiApplication::primaryScreen()
return QGuiApplicationPrivate::screen_list.at(0);
}
+/*!
+ Returns a list of all the screens associated with the
+ windowing system the application is connected to.
+*/
QList<QScreen *> QGuiApplication::screens()
{
return QGuiApplicationPrivate::screen_list;
}
+/*!
+ Returns the top level window at the given position, if any.
+*/
QWindow *QGuiApplication::topLevelAt(const QPoint &pos)
{
QList<QScreen *> screens = QGuiApplication::screens();
@@ -517,8 +705,8 @@ QGuiApplicationPrivate::~QGuiApplicationPrivate()
delete generic_plugin_list.at(i);
generic_plugin_list.clear();
- delete app_font;
- app_font = 0;
+ clearFontUnlocked();
+
QFont::cleanup();
#ifndef QT_NO_CURSOR
@@ -557,27 +745,62 @@ static QClipboard *clipboard();
#endif
#endif
+/*!
+ Returns the currently held keyboard modifiers.
+*/
Qt::KeyboardModifiers QGuiApplication::keyboardModifiers()
{
return QGuiApplicationPrivate::modifier_buttons;
}
+/*!
+ Returns the currently held mouse buttons.
+*/
Qt::MouseButtons QGuiApplication::mouseButtons()
{
return QGuiApplicationPrivate::mouse_buttons;
}
+/*!
+ Returns the platform's native interface, for platform specific
+ functionality.
+*/
QPlatformNativeInterface *QGuiApplication::platformNativeInterface()
{
QPlatformIntegration *pi = QGuiApplicationPrivate::platformIntegration();
return pi->nativeInterface();
}
+/*!
+ Enters the main event loop and waits until exit() is called, and then
+ returns the value that was set to exit() (which is 0 if exit() is called
+ via quit()).
+
+ It is necessary to call this function to start event handling. The main
+ event loop receives events from the window system and dispatches these to
+ the application widgets.
+
+ Generally, no user interaction can take place before calling exec().
+
+ To make your application perform idle processing, e.g., executing a special
+ function whenever there are no pending events, use a QTimer with 0 timeout.
+ More advanced idle processing schemes can be achieved using processEvents().
+
+ We recommend that you connect clean-up code to the
+ \l{QCoreApplication::}{aboutToQuit()} signal, instead of putting it in your
+ application's \c{main()} function. This is because, on some platforms, the
+ QApplication::exec() call may not return.
+
+ \sa quitOnLastWindowClosed, quit(), exit(), processEvents(),
+ QCoreApplication::exec()
+*/
int QGuiApplication::exec()
{
return QCoreApplication::exec();
}
+/*! \reimp
+*/
bool QGuiApplication::notify(QObject *object, QEvent *event)
{
#ifndef QT_NO_SHORTCUT
@@ -595,6 +818,8 @@ bool QGuiApplication::notify(QObject *object, QEvent *event)
return QCoreApplication::notify(object, event);
}
+/*! \reimp
+*/
bool QGuiApplication::event(QEvent *e)
{
if(e->type() == QEvent::LanguageChange) {
@@ -603,6 +828,9 @@ bool QGuiApplication::event(QEvent *e)
return QCoreApplication::event(e);
}
+/*!
+ \internal
+*/
bool QGuiApplication::compressEvent(QEvent *event, QObject *receiver, QPostEventList *postedEvents)
{
return QCoreApplication::compressEvent(event, receiver, postedEvents);
@@ -804,8 +1032,7 @@ void QGuiApplicationPrivate::processWheelEvent(QWindowSystemInterfacePrivate::Wh
QWindow *window = e->window.data();
if (window) {
- QWheelEvent ev(e->localPos, e->globalPos, e->delta, buttons, e->modifiers,
- e->orient);
+ QWheelEvent ev(e->localPos, e->globalPos, e->pixelDelta, e->angleDelta, e->qt4Delta, e->qt4Orientation, buttons, e->modifiers);
ev.setTimestamp(e->timestamp);
QGuiApplication::sendSpontaneousEvent(window, &ev);
return;
@@ -896,6 +1123,8 @@ void QGuiApplicationPrivate::processWindowStateChangedEvent(QWindowSystemInterfa
void QGuiApplicationPrivate::processThemeChanged(QWindowSystemInterfacePrivate::ThemeChangeEvent *tce)
{
+ if (self)
+ self->notifyThemeChanged();
if (QWindow *window = tce->window.data()) {
QEvent e(QEvent::ThemeChange);
QGuiApplication::sendSpontaneousEvent(window, &e);
@@ -1364,6 +1593,9 @@ Qt::DropAction QGuiApplicationPrivate::processDrop(QWindow *w, QMimeData *dropDa
}
#ifndef QT_NO_CLIPBOARD
+/*!
+ Returns the object for interacting with the clipboard.
+*/
QClipboard * QGuiApplication::clipboard()
{
if (QGuiApplicationPrivate::qt_clipboard == 0) {
@@ -1378,20 +1610,22 @@ QClipboard * QGuiApplication::clipboard()
#endif
/*!
- Returns the application palette.
+ Returns the default application palette.
- \sa setPalette(), QWidget::palette()
+ \sa setPalette()
*/
+
QPalette QGuiApplication::palette()
{
- if (!QGuiApplicationPrivate::app_pal)
- if (const QPalette *themePalette = QGuiApplicationPrivate::platformTheme()->palette())
- QGuiApplicationPrivate::app_pal = new QPalette(*themePalette);
- if (!QGuiApplicationPrivate::app_pal)
- QGuiApplicationPrivate::app_pal = new QPalette(Qt::black);
+ initPalette();
return *QGuiApplicationPrivate::app_pal;
}
+/*!
+ Changes the default application palette to \a palette.
+
+ \sa palette()
+*/
void QGuiApplication::setPalette(const QPalette &pal)
{
if (QGuiApplicationPrivate::app_pal && pal.isCopyOf(*QGuiApplicationPrivate::app_pal))
@@ -1400,17 +1634,26 @@ void QGuiApplication::setPalette(const QPalette &pal)
QGuiApplicationPrivate::app_pal = new QPalette(pal);
else
*QGuiApplicationPrivate::app_pal = pal;
+ applicationResourceFlags |= ApplicationPaletteExplicitlySet;
}
+/*!
+ Returns the default application font.
+
+ \sa setFont()
+*/
QFont QGuiApplication::font()
{
QMutexLocker locker(&applicationFontMutex);
- if (!QGuiApplicationPrivate::app_font)
- QGuiApplicationPrivate::app_font =
- new QFont(QGuiApplicationPrivate::platformIntegration()->fontDatabase()->defaultFont());
+ initFontUnlocked();
return *QGuiApplicationPrivate::app_font;
}
+/*!
+ Changes the default application font to \a font.
+
+ \sa font()
+*/
void QGuiApplication::setFont(const QFont &font)
{
QMutexLocker locker(&applicationFontMutex);
@@ -1418,6 +1661,7 @@ void QGuiApplication::setFont(const QFont &font)
QGuiApplicationPrivate::app_font = new QFont(font);
else
*QGuiApplicationPrivate::app_font = font;
+ applicationResourceFlags |= ApplicationFontExplicitlySet;
}
/*!
@@ -1631,7 +1875,7 @@ void QGuiApplication::restoreOverrideCursor()
/*!
\since 5.0
- returns the style hints.
+ Returns the application's style hints.
The style hints encapsulate a set of platform dependent properties
such as double click intervals, full width selection and others.
@@ -1675,6 +1919,14 @@ bool QGuiApplication::desktopSettingsAware()
return QGuiApplicationPrivate::obey_desktop_settings;
}
+QInputMethod *QGuiApplication::inputMethod() const
+{
+ Q_D(const QGuiApplication);
+ if (!d->inputMethod)
+ const_cast<QGuiApplicationPrivate *>(d)->inputMethod = new QInputMethod();
+ return d->inputMethod;
+}
+
/*!
\since 5.0
@@ -1686,40 +1938,11 @@ bool QGuiApplication::desktopSettingsAware()
\sa QInputPanel
*/
-QInputMethod *QGuiApplication::inputMethod() const
-{
- Q_D(const QGuiApplication);
- if (!d->inputMethod)
- const_cast<QGuiApplicationPrivate *>(d)->inputMethod = new QInputMethod();
- return d->inputMethod;
-}
-
QInputPanel *QGuiApplication::inputPanel() const
{
return inputMethod();
}
-
-// Returns the current platform used by keyBindings
-uint QGuiApplicationPrivate::currentKeyPlatform()
-{
- uint platform = KB_Win;
-#ifdef Q_OS_MAC
- platform = KB_Mac;
-#elif defined Q_WS_X11 // ## TODO: detect these
- platform = KB_X11;
-#if 0
- if (X11->desktopEnvironment == DE_KDE)
- platform |= KB_KDE;
- if (X11->desktopEnvironment == DE_GNOME)
- platform |= KB_Gnome;
- if (X11->desktopEnvironment == DE_CDE)
- platform |= KB_CDE;
-#endif
-#endif
- return platform;
-}
-
/*!
\since 4.5
\fn void QGuiApplication::fontDatabaseChanged()
@@ -1843,4 +2066,17 @@ QPixmap QGuiApplicationPrivate::getPixmapCursor(Qt::CursorShape cshape)
return QPixmap();
}
+void QGuiApplicationPrivate::notifyThemeChanged()
+{
+ if (!(applicationResourceFlags & ApplicationPaletteExplicitlySet)) {
+ clearPalette();
+ initPalette();
+ }
+ if (!(applicationResourceFlags & ApplicationFontExplicitlySet)) {
+ QMutexLocker locker(&applicationFontMutex);
+ clearFontUnlocked();
+ initFontUnlocked();
+ }
+}
+
QT_END_NAMESPACE