2 * Copyright © 2003-2007 Fredrik Höglund <fredrik@kde.org>
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public
6 * License version 2 as published by the Free Software Foundation.
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 * General Public License for more details.
13 * You should have received a copy of the GNU General Public License
14 * along with this program; see the file COPYING. If not, write to
15 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
16 * Boston, MA 02110-1301, USA.
21 #include <QMouseEvent>
23 #include "previewwidget.h"
26 #include <X11/Xcursor/Xcursor.h>
33 const char *const cursorNames
[] = {
50 const int numCursors
= 9; // The number of cursors from the above list to be previewed
51 const int previewSize
= 24; // The nominal cursor size to be used in the preview widget
52 const int cursorSpacing
= 20; // Spacing between preview cursors
53 const int widgetMinWidth
= 10; // The minimum width of the preview widget
54 const int widgetMinHeight
= 48; // The minimum height of the preview widget
58 ///////////////////////////////////////////////////////////////////////////////
61 PreviewCursor (const XCursorTheme
&theme
, const QString
&name
);
64 const QPixmap
&pixmap () const { return mPixmap
; }
65 Cursor
handle () const { return mCursor
.handle(); }
66 int width () const { return mPixmap
.width(); }
67 int height () const { return mPixmap
.height(); }
68 inline QRect
rect () const;
69 void setPosition (const QPoint
&p
) { mPos
= p
; }
70 void setPosition (int x
, int y
) { mPos
= QPoint(x
, y
); }
71 QPoint
position () const { return mPos
; }
72 operator const QCursor
& () const { return mCursor
; }
73 operator const QPixmap
& () const { return pixmap(); }
82 ///////////////////////////////////////////////////////////////////////////////
83 PreviewCursor::PreviewCursor (const XCursorTheme
&theme
, const QString
&name
) {
84 // Create the preview pixmap
85 QImage image
= theme
.loadImage(name
, previewSize
);
86 if (image
.isNull()) return;
87 int maxSize
= previewSize
*2;
88 if (image
.height() > maxSize
|| image
.width() > maxSize
)
89 image
= image
.scaled(maxSize
, maxSize
, Qt::KeepAspectRatio
, Qt::SmoothTransformation
);
90 mPixmap
= QPixmap::fromImage(image
);
92 mCursor
= theme
.loadCursor(name
, previewSize
);
96 QRect
PreviewCursor::rect () const {
97 return QRect(mPos
, mPixmap
.size()).adjusted(-(cursorSpacing
/2), -(cursorSpacing
/2), cursorSpacing
/2, cursorSpacing
/2);
101 ///////////////////////////////////////////////////////////////////////////////
102 PreviewWidget::PreviewWidget (QWidget
*parent
) : QWidget(parent
) {
103 setMouseTracking(true);
108 PreviewWidget::~PreviewWidget () {
114 QSize
PreviewWidget::sizeHint () const {
117 foreach (const PreviewCursor
*c
, list
) {
118 totalWidth
+= c
->width();
119 maxHeight
= qMax(c
->height(), maxHeight
);
121 totalWidth
+= (list
.count()-1)*cursorSpacing
;
122 maxHeight
= qMax(maxHeight
, widgetMinHeight
);
123 return QSize(qMax(totalWidth
, widgetMinWidth
), qMax(height(), maxHeight
));
127 void PreviewWidget::layoutItems () {
128 if (!list
.isEmpty()) {
129 QSize size
= sizeHint();
130 int cursorWidth
= size
.width()/list
.count();
131 int nextX
= (width()-size
.width())/2;
132 foreach (PreviewCursor
*c
, list
) {
133 c
->setPosition(nextX
+(cursorWidth
-c
->width())/2, (height()-c
->height())/2);
134 nextX
+= cursorWidth
;
141 void PreviewWidget::setTheme (const XCursorTheme
&theme
) {
144 for (int i
= 0; i
< numCursors
; i
++) list
<< new PreviewCursor(theme
, cursorNames
[i
]);
152 void PreviewWidget::paintEvent (QPaintEvent
*) {
154 if (needLayout
) layoutItems();
155 foreach (const PreviewCursor
*c
, list
) {
156 if (c
->pixmap().isNull()) continue;
157 p
.drawPixmap(c
->position(), *c
);
162 void PreviewWidget::mouseMoveEvent (QMouseEvent
*e
) {
163 if (needLayout
) layoutItems();
164 foreach (const PreviewCursor
*c
, list
) {
165 if (c
->rect().contains(e
->pos())) {
173 setCursor(Qt::ArrowCursor
);
178 void PreviewWidget::resizeEvent (QResizeEvent
*) {
179 if (!list
.isEmpty()) needLayout
= true;