1 /*****************************************************************************
2 * Copyright © 2011-2012 VideoLAN
5 * Authors: Ludovic Fauvet <etix@l0cal.com>
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
20 *****************************************************************************/
22 #include "timetooltip.hpp"
24 #include <QApplication>
26 #include <QPainterPath>
28 #include <QFontMetrics>
29 #include <QDesktopWidget>
33 TimeTooltip::TimeTooltip( QWidget *parent ) :
34 QWidget( parent ), mInitialized( false )
36 setWindowFlags( Qt::Window |
37 Qt::WindowStaysOnTopHint |
38 Qt::FramelessWindowHint |
39 Qt::X11BypassWindowManagerHint );
41 // Tell Qt that it doesn't need to erase the background before
42 // a paintEvent occurs. This should save some CPU cycles.
43 setAttribute( Qt::WA_OpaquePaintEvent );
47 - This attribute is required on Windows to avoid focus stealing of other windows.
48 - When set on Linux the TimeTooltip appears behind the FSController in fullscreen.
50 setAttribute( Qt::WA_ShowWithoutActivating );
53 // Inherit from the system default font size -5
54 mFont = QFont( "Verdana", qMax( qApp->font().pointSize() - 5, 7 ) );
58 void TimeTooltip::adjustPosition()
60 // Get the bounding box required to print the text and add some padding
61 QFontMetrics metrics( mFont );
62 QRect textbox = metrics.boundingRect( mDisplayedText );
63 textbox.adjust( -2, -2, 2, 2 );
64 textbox.moveTo( 0, 0 );
66 // Resize the widget to fit our needs
67 QSize size( textbox.width() + 1, textbox.height() + TIP_HEIGHT + 1 );
69 // The desired label position is just above the target
70 QPoint position( mTarget.x() - size.width() / 2,
71 mTarget.y() - size.height() + TIP_HEIGHT / 2 );
73 // Keep the tooltip on the same screen if possible
74 QRect screen = QApplication::desktop()->screenGeometry( mTarget );
75 position.setX( qMax( screen.left(), qMin( position.x(),
76 screen.left() + screen.width() - size.width() ) ) );
77 position.setY( qMax( screen.top(), qMin( position.y(),
78 screen.top() + screen.height() - size.height() ) ) );
82 int tipX = mTarget.x() - position.x();
83 if( mBox != textbox || mTipX != tipX )
94 void TimeTooltip::buildPath()
96 // Prepare the painter path for future use so
97 // we only have to generate the text at runtime.
100 mPainterPath = QPainterPath();
101 mPainterPath.addRect( mBox );
105 polygon << QPoint( qMax( 0, mTipX - 3 ), mBox.height() )
106 << QPoint( mTipX, mBox.height() + TIP_HEIGHT )
107 << QPoint( qMin( mTipX + 3, mBox.width() ), mBox.height() );
108 mPainterPath.addPolygon( polygon );
110 // Store the simplified version of the path
111 mPainterPath = mPainterPath.simplified();
113 // Create the mask used to erase the background
114 // Note: this is a binary bitmap (black & white)
115 mMask = QBitmap( size() );
116 QPainter painter( &mMask );
117 painter.fillRect( mMask.rect(), Qt::white );
118 painter.setPen( Qt::black );
119 painter.setBrush( Qt::black );
120 painter.drawPath( mPainterPath );
124 void TimeTooltip::setTip( const QPoint& target, const QString& time, const QString& text )
127 mDisplayedText = time;
128 if ( !text.isEmpty() )
129 mDisplayedText.append( " - " ).append( text );
131 if( mTarget != target || time.length() != mTime.length() || mText != text )
142 void TimeTooltip::show()
144 QWidget::setVisible( mInitialized );
147 void TimeTooltip::paintEvent( QPaintEvent * )
150 p.setRenderHints( QPainter::HighQualityAntialiasing | QPainter::TextAntialiasing );
152 p.setPen( Qt::black );
153 p.setBrush( qApp->palette().base() );
154 p.drawPath( mPainterPath );
157 p.setPen( QPen( qApp->palette().text(), 1 ) );
158 p.drawText( mBox, Qt::AlignCenter, mDisplayedText );