1 // vim: set tabstop=4 shiftwidth=4 noexpandtab:
3 Gwenview: an image viewer
4 Copyright 2007 Aurélien Gâteau <aurelien.gateau@free.fr>
6 This program is free software; you can redistribute it and/or
7 modify it under the terms of the GNU General Public License
8 as published by the Free Software Foundation; either version 2
9 of the License, or (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
22 #include "fullscreenbar.moc"
26 #include <QApplication>
27 #include <QDesktopWidget>
32 #include <QToolButton>
43 static const int SLIDE_DURATION
= 150;
44 static const int AUTO_HIDE_CURSOR_TIMEOUT
= 1000;
46 // How long before the bar slide out after switching to fullscreen
47 static const int INITIAL_HIDE_TIMEOUT
= 2000;
50 struct FullScreenBarPrivate
{
53 QTimer
* mAutoHideCursorTimer
;
54 bool mAutoHidingEnabled
;
56 void startTimeLine() {
57 if (mTimeLine
->state() != QTimeLine::Running
) {
63 QBitmap
empty(32, 32);
65 QCursor
blankCursor(empty
, empty
);
66 QApplication::setOverrideCursor(blankCursor
);
70 * Returns the rectangle in which the mouse must enter to trigger bar
71 * sliding. The rectangle is in global coords.
73 QRect
slideInTriggerRect() const {
74 QRect rect
= QApplication::desktop()->screenGeometry();
75 // Take parent widget position into account because it may not be at
76 // the top of the screen, for example when the save bar warning is
78 const QPoint topLeft
= that
->parentWidget()->mapToGlobal(QPoint(0, 0));
79 rect
.setHeight(topLeft
.y() + that
->height());
83 bool shouldHide() const {
84 Q_ASSERT(that
->parentWidget());
86 if (!mAutoHidingEnabled
) {
89 if (slideInTriggerRect().contains(QCursor::pos())) {
92 if (qApp
->activePopupWidget()) {
100 FullScreenBar::FullScreenBar(QWidget
* parent
)
102 , d(new FullScreenBarPrivate
) {
104 d
->mAutoHidingEnabled
= true;
105 setObjectName("fullScreenBar");
107 d
->mTimeLine
= new QTimeLine(SLIDE_DURATION
, this);
108 connect(d
->mTimeLine
, SIGNAL(valueChanged(qreal
)), SLOT(moveBar(qreal
)) );
110 d
->mAutoHideCursorTimer
= new QTimer(this);
111 d
->mAutoHideCursorTimer
->setInterval(AUTO_HIDE_CURSOR_TIMEOUT
);
112 d
->mAutoHideCursorTimer
->setSingleShot(true);
113 connect(d
->mAutoHideCursorTimer
, SIGNAL(timeout()), SLOT(slotAutoHideCursorTimeout()) );
119 FullScreenBar::~FullScreenBar() {
123 QSize
FullScreenBar::sizeHint() const {
124 int width
= QApplication::desktop()->screenGeometry(this).width();
125 return QSize(width
, QFrame::sizeHint().height());
128 void FullScreenBar::moveBar(qreal value
) {
129 move(0, -height() + int(value
* height()) );
131 // For some reason, if Gwenview is started with command line options to
132 // start a slideshow, the bar might end up below the view. Calling raise()
138 void FullScreenBar::setActivated(bool activated
) {
140 // Delay installation of event filter because switching to fullscreen
141 // cause a few window adjustments, which seems to generate unwanted
142 // mouse events, which cause the bar to slide in.
143 QTimer::singleShot(500, this, SLOT(delayedInstallEventFilter()));
145 // Make sure the widget is visible on start
150 qApp
->removeEventFilter(this);
152 d
->mAutoHideCursorTimer
->stop();
153 QApplication::restoreOverrideCursor();
158 void FullScreenBar::delayedInstallEventFilter() {
159 qApp
->installEventFilter(this);
160 if (d
->shouldHide()) {
161 QTimer::singleShot(INITIAL_HIDE_TIMEOUT
, this, SLOT(slideOut()));
167 void FullScreenBar::slotAutoHideCursorTimeout() {
168 if (d
->shouldHide()) {
171 d
->mAutoHideCursorTimer
->start();
176 void FullScreenBar::slideOut() {
177 d
->mTimeLine
->setDirection(QTimeLine::Backward
);
182 void FullScreenBar::slideIn() {
183 d
->mTimeLine
->setDirection(QTimeLine::Forward
);
188 bool FullScreenBar::eventFilter(QObject
* object
, QEvent
* event
) {
189 if (event
->type() == QEvent::MouseMove
) {
190 QApplication::restoreOverrideCursor();
191 d
->mAutoHideCursorTimer
->start();
193 if (d
->shouldHide()) {
197 if (d
->slideInTriggerRect().contains(QCursor::pos())) {
204 // Filtering message on tooltip text for CJK to remove accelerators.
205 // Quoting ktoolbar.cpp:
207 // CJK languages use more verbose accelerator marker: they add a Latin
208 // letter in parenthesis, and put accelerator on that. Hence, the default
209 // removal of ampersand only may not be enough there, instead the whole
210 // parenthesis construct should be removed. Provide these filtering i18n
211 // messages so that translators can use Transcript for custom removal.
213 if (event
->type() == QEvent::Show
|| event
->type() == QEvent::Paint
) {
214 QToolButton
* button
= qobject_cast
<QToolButton
*>(object
);
215 if (button
&& !button
->actions().isEmpty()) {
216 QAction
* action
= button
->actions().first();
217 button
->setToolTip(i18nc("@info:tooltip of custom toolbar button", "%1", action
->toolTip()));
225 void FullScreenBar::setAutoHidingEnabled(bool value
) {
226 d
->mAutoHidingEnabled
= value
;