source: trunk/src/gui/widgets/qsplashscreen.cpp@ 846

Last change on this file since 846 was 846, checked in by Dmitry A. Kuminov, 14 years ago

trunk: Merged in qt 4.7.2 sources from branches/vendor/nokia/qt.

File size: 10.4 KB
Line 
1/****************************************************************************
2**
3** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
4** All rights reserved.
5** Contact: Nokia Corporation ([email protected])
6**
7** This file is part of the QtGui module of the Qt Toolkit.
8**
9** $QT_BEGIN_LICENSE:LGPL$
10** Commercial Usage
11** Licensees holding valid Qt Commercial licenses may use this file in
12** accordance with the Qt Commercial License Agreement provided with the
13** Software or, alternatively, in accordance with the terms contained in
14** a written agreement between you and Nokia.
15**
16** GNU Lesser General Public License Usage
17** Alternatively, this file may be used under the terms of the GNU Lesser
18** General Public License version 2.1 as published by the Free Software
19** Foundation and appearing in the file LICENSE.LGPL included in the
20** packaging of this file. Please review the following information to
21** ensure the GNU Lesser General Public License version 2.1 requirements
22** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
23**
24** In addition, as a special exception, Nokia gives you certain additional
25** rights. These rights are described in the Nokia Qt LGPL Exception
26** version 1.1, included in the file LGPL_EXCEPTION.txt in this 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 have questions regarding the use of this file, please contact
37** Nokia at [email protected].
38** $QT_END_LICENSE$
39**
40****************************************************************************/
41
42#include "qsplashscreen.h"
43
44#ifndef QT_NO_SPLASHSCREEN
45
46#include "qapplication.h"
47#include "qdesktopwidget.h"
48#include "qpainter.h"
49#include "qpixmap.h"
50#include "qtextdocument.h"
51#include "qtextcursor.h"
52#include <QtCore/qdebug.h>
53#include <private/qwidget_p.h>
54
55QT_BEGIN_NAMESPACE
56
57class QSplashScreenPrivate : public QWidgetPrivate
58{
59 Q_DECLARE_PUBLIC(QSplashScreen)
60public:
61 QPixmap pixmap;
62 QString currStatus;
63 QColor currColor;
64 int currAlign;
65
66 inline QSplashScreenPrivate();
67 void drawContents();
68};
69
70/*!
71 \class QSplashScreen
72 \brief The QSplashScreen widget provides a splash screen that can
73 be shown during application startup.
74
75 A splash screen is a widget that is usually displayed when an
76 application is being started. Splash screens are often used for
77 applications that have long start up times (e.g. database or
78 networking applications that take time to establish connections) to
79 provide the user with feedback that the application is loading.
80
81 The splash screen appears in the center of the screen. It may be
82 useful to add the Qt::WindowStaysOnTopHint to the splash widget's
83 window flags if you want to keep it above all the other windows on
84 the desktop.
85
86 Some X11 window managers do not support the "stays on top" flag. A
87 solution is to set up a timer that periodically calls raise() on
88 the splash screen to simulate the "stays on top" effect.
89
90 The most common usage is to show a splash screen before the main
91 widget is displayed on the screen. This is illustrated in the
92 following code snippet in which a splash screen is displayed and
93 some initialization tasks are performed before the application's
94 main window is shown:
95
96 \snippet doc/src/snippets/qsplashscreen/main.cpp 0
97 \dots
98 \snippet doc/src/snippets/qsplashscreen/main.cpp 1
99
100 The user can hide the splash screen by clicking on it with the
101 mouse. Since the splash screen is typically displayed before the
102 event loop has started running, it is necessary to periodically
103 call QApplication::processEvents() to receive the mouse clicks.
104
105 It is sometimes useful to update the splash screen with messages,
106 for example, announcing connections established or modules loaded
107 as the application starts up:
108
109 \snippet doc/src/snippets/code/src_gui_widgets_qsplashscreen.cpp 0
110
111 QSplashScreen supports this with the showMessage() function. If you
112 wish to do your own drawing you can get a pointer to the pixmap
113 used in the splash screen with pixmap(). Alternatively, you can
114 subclass QSplashScreen and reimplement drawContents().
115*/
116
117/*!
118 Construct a splash screen that will display the \a pixmap.
119
120 There should be no need to set the widget flags, \a f, except
121 perhaps Qt::WindowStaysOnTopHint.
122*/
123QSplashScreen::QSplashScreen(const QPixmap &pixmap, Qt::WindowFlags f)
124 : QWidget(*(new QSplashScreenPrivate()), 0, Qt::SplashScreen | f)
125{
126 d_func()->pixmap = pixmap;
127 setPixmap(d_func()->pixmap); // Does an implicit repaint
128}
129
130/*!
131 \overload
132
133 This function allows you to specify a parent for your splashscreen. The
134 typical use for this constructor is if you have a multiple screens and
135 prefer to have the splash screen on a different screen than your primary
136 one. In that case pass the proper desktop() as the \a parent.
137*/
138QSplashScreen::QSplashScreen(QWidget *parent, const QPixmap &pixmap, Qt::WindowFlags f)
139 : QWidget(*new QSplashScreenPrivate, parent, Qt::SplashScreen | f)
140{
141 d_func()->pixmap = pixmap;
142 setPixmap(d_func()->pixmap); // Does an implicit repaint
143}
144
145/*!
146 Destructor.
147*/
148QSplashScreen::~QSplashScreen()
149{
150}
151
152/*!
153 \reimp
154*/
155void QSplashScreen::mousePressEvent(QMouseEvent *)
156{
157 hide();
158}
159
160/*!
161 This overrides QWidget::repaint(). It differs from the standard
162 repaint function in that it also calls QApplication::flush() to
163 ensure the updates are displayed, even when there is no event loop
164 present.
165*/
166void QSplashScreen::repaint()
167{
168 d_func()->drawContents();
169 QWidget::repaint();
170 QApplication::flush();
171}
172
173/*!
174 \fn QSplashScreen::messageChanged(const QString &message)
175
176 This signal is emitted when the message on the splash screen
177 changes. \a message is the new message and is a null-string
178 when the message has been removed.
179
180 \sa showMessage(), clearMessage()
181*/
182
183
184
185/*!
186 Draws the \a message text onto the splash screen with color \a
187 color and aligns the text according to the flags in \a alignment.
188
189 To make sure the splash screen is repainted immediately, you can
190 call \l{QCoreApplication}'s
191 \l{QCoreApplication::}{processEvents()} after the call to
192 showMessage(). You usually want this to make sure that the message
193 is kept up to date with what your application is doing (e.g.,
194 loading files).
195
196 \sa Qt::Alignment, clearMessage()
197*/
198void QSplashScreen::showMessage(const QString &message, int alignment,
199 const QColor &color)
200{
201 Q_D(QSplashScreen);
202 d->currStatus = message;
203 d->currAlign = alignment;
204 d->currColor = color;
205 emit messageChanged(d->currStatus);
206 repaint();
207}
208
209/*!
210 Removes the message being displayed on the splash screen
211
212 \sa showMessage()
213 */
214void QSplashScreen::clearMessage()
215{
216 d_func()->currStatus.clear();
217 emit messageChanged(d_func()->currStatus);
218 repaint();
219}
220
221/*!
222 Makes the splash screen wait until the widget \a mainWin is displayed
223 before calling close() on itself.
224*/
225void QSplashScreen::finish(QWidget *mainWin)
226{
227 if (mainWin) {
228#if defined(Q_WS_X11)
229 extern void qt_x11_wait_for_window_manager(QWidget *mainWin);
230 qt_x11_wait_for_window_manager(mainWin);
231#endif
232 }
233 close();
234}
235
236/*!
237 Sets the pixmap that will be used as the splash screen's image to
238 \a pixmap.
239*/
240void QSplashScreen::setPixmap(const QPixmap &pixmap)
241{
242 Q_D(QSplashScreen);
243
244 if (pixmap.hasAlpha()) {
245 QPixmap opaque(pixmap.size());
246 QPainter p(&opaque);
247 p.fillRect(0, 0, pixmap.width(), pixmap.height(), palette().background());
248 p.drawPixmap(0, 0, pixmap);
249 p.end();
250 d->pixmap = opaque;
251 } else {
252 d->pixmap = pixmap;
253 }
254
255 QRect r(0, 0, d->pixmap.size().width(), d->pixmap.size().height());
256 resize(d->pixmap.size());
257 move(QApplication::desktop()->screenGeometry().center() - r.center());
258 if (!isVisible())
259 d->drawContents();
260 else
261 repaint();
262}
263
264/*!
265 Returns the pixmap that is used in the splash screen. The image
266 does not have any of the text drawn by showMessage() calls.
267*/
268const QPixmap QSplashScreen::pixmap() const
269{
270 return d_func()->pixmap;
271}
272
273/*!
274 \internal
275*/
276void QSplashScreenPrivate::drawContents()
277{
278 Q_Q(QSplashScreen);
279 QPixmap textPix = pixmap;
280 if (!textPix.isNull()) {
281 QPainter painter(&textPix);
282 painter.initFrom(q);
283 q->drawContents(&painter);
284 QPalette p = q->palette();
285 p.setBrush(q->backgroundRole(), QBrush(textPix));
286 q->setPalette(p);
287 }
288}
289
290/*!
291 \internal
292*/
293inline QSplashScreenPrivate::QSplashScreenPrivate() : currAlign(Qt::AlignLeft)
294{
295}
296
297/*!
298 Draw the contents of the splash screen using painter \a painter.
299 The default implementation draws the message passed by showMessage().
300 Reimplement this function if you want to do your own drawing on
301 the splash screen.
302*/
303void QSplashScreen::drawContents(QPainter *painter)
304{
305 Q_D(QSplashScreen);
306 painter->setPen(d->currColor);
307 QRect r = rect();
308 r.setRect(r.x() + 5, r.y() + 5, r.width() - 10, r.height() - 10);
309 if (Qt::mightBeRichText(d->currStatus)) {
310 QTextDocument doc;
311#ifdef QT_NO_TEXTHTMLPARSER
312 doc.setPlainText(d->currStatus);
313#else
314 doc.setHtml(d->currStatus);
315#endif
316 doc.setTextWidth(r.width());
317 QTextCursor cursor(&doc);
318 cursor.select(QTextCursor::Document);
319 QTextBlockFormat fmt;
320 fmt.setAlignment(Qt::Alignment(d->currAlign));
321 cursor.mergeBlockFormat(fmt);
322 painter->save();
323 painter->translate(r.topLeft());
324 doc.drawContents(painter);
325 painter->restore();
326 } else {
327 painter->drawText(r, d->currAlign, d->currStatus);
328 }
329}
330
331/*!
332 \fn void QSplashScreen::message(const QString &message, int alignment,
333 const QColor &color)
334 \compat
335
336 Use showMessage() instead.
337*/
338
339/*!
340 \fn void QSplashScreen::clear()
341 \compat
342
343 Use clearMessage() instead.
344*/
345
346/*! \reimp */
347bool QSplashScreen::event(QEvent *e)
348{
349 return QWidget::event(e);
350}
351
352QT_END_NAMESPACE
353
354#endif //QT_NO_SPLASHSCREEN
Note: See TracBrowser for help on using the repository browser.