• Skip to content
  • Skip to link menu
KDE 4.3 API Reference
  • KDE API Reference
  • kdelibs
  • Sitemap
  • Contact Us
 

KDEUI

kanimatedbutton.cpp

Go to the documentation of this file.
00001 /* This file is part of the KDE libraries
00002    Copyright (C) 2000 Kurt Granroth <granroth@kde.org>
00003    Copyright (C) 2006 Hamish Rodda <rodda@kde.org>
00004    Copyright (C) 2008 Pino Toscano <pino@kde.org>
00005 
00006    This library is free software; you can redistribute it and/or
00007    modify it under the terms of the GNU Library General Public
00008    License version 2 as published by the Free Software Foundation.
00009 
00010    This library is distributed in the hope that it will be useful,
00011    but WITHOUT ANY WARRANTY; without even the implied warranty of
00012    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013    Library General Public License for more details.
00014 
00015    You should have received a copy of the GNU Library General Public License
00016    along with this library; see the file COPYING.LIB.  If not, write to
00017    the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
00018    Boston, MA 02110-1301, USA.
00019 */
00020 
00021 #include <kanimatedbutton.h>
00022 
00023 #include <QAction>
00024 #include <QPixmap>
00025 #include <QTimer>
00026 #include <QImage>
00027 #include <QToolBar>
00028 #include <QPainter>
00029 #include <QMovie>
00030 
00031 #include <kdebug.h>
00032 #include <kiconloader.h>
00033 
00034 class KAnimatedButtonPrivate
00035 {
00036 public:
00037     KAnimatedButtonPrivate(KAnimatedButton *qq)
00038         : q(qq), movie(0)
00039     {
00040     }
00041 
00042     void updateCurrentIcon();
00043     void _k_movieFrameChanged(int number);
00044     void _k_movieFinished();
00045 
00046     KAnimatedButton *q;
00047     QMovie *movie;
00048 
00049   int                    frames;
00050   int                    current_frame;
00051   QPixmap                pixmap;
00052   QTimer                 timer;
00053   QString                icon_name;
00054   QVector<QPixmap*>      framesCache; // We keep copies of each frame so that
00055                                       // the icon code can properly cache them in QPixmapCache,
00056                                       // and not fill it up with dead copies
00057 };
00058 
00059 KAnimatedButton::KAnimatedButton( QWidget *parent )
00060     : QToolButton(parent), d(new KAnimatedButtonPrivate(this))
00061 {
00062   connect( &d->timer, SIGNAL(timeout()), this, SLOT(slotTimerUpdate()));
00063 }
00064 
00065 KAnimatedButton::~KAnimatedButton()
00066 {
00067   d->timer.stop();
00068   qDeleteAll(d->framesCache);
00069   delete d->movie;
00070 
00071   delete d;
00072 }
00073 
00074 void KAnimatedButton::start()
00075 {
00076     if (d->movie) {
00077         d->movie->start();
00078     } else {
00079         d->current_frame = 0;
00080         d->timer.start(50);
00081     }
00082 }
00083 
00084 void KAnimatedButton::stop()
00085 {
00086     if (d->movie) {
00087         d->movie->stop();
00088         d->movie->jumpToFrame(0);
00089         d->_k_movieFrameChanged(0);
00090     } else {
00091        d->current_frame = 0;
00092        d->timer.stop();
00093        d->updateCurrentIcon();
00094     }
00095 }
00096 
00097 void KAnimatedButton::setIcons( const QString& icons )
00098 {
00099   if ( d->icon_name == icons )
00100     return;
00101 
00102   d->timer.stop();
00103   d->icon_name = icons;
00104   updateIcons();
00105 }
00106 
00107 QString KAnimatedButton::icons( ) const
00108 {
00109    return d->icon_name;
00110 }
00111 
00112 void KAnimatedButton::slotTimerUpdate()
00113 {
00114   if(!isVisible())
00115     return;
00116 
00117   d->current_frame++;
00118   if (d->current_frame == d->frames)
00119      d->current_frame = 0;
00120 
00121   d->updateCurrentIcon();
00122 }
00123 
00124 void KAnimatedButtonPrivate::updateCurrentIcon()
00125 {
00126   if (pixmap.isNull())
00127     return;
00128 
00129   QPixmap* frame = framesCache[current_frame];
00130   if (!frame)
00131   {
00132         const int icon_size = q->iconDimensions();
00133         const int row_size = pixmap.width() / icon_size;
00134         const int row = current_frame / row_size;
00135         const int column = current_frame % row_size;
00136         frame = new QPixmap(icon_size, icon_size);
00137     frame->fill(Qt::transparent);
00138     QPainter p(frame);
00139         p.drawPixmap(QPoint(0, 0), pixmap, QRect(column * icon_size, row * icon_size, icon_size, icon_size));
00140     p.end();
00141     framesCache[current_frame] = frame;
00142   }
00143 
00144   q->setIcon(QIcon(*frame));
00145 }
00146 
00147 void KAnimatedButtonPrivate::_k_movieFrameChanged(int number)
00148 {
00149     Q_UNUSED(number);
00150     q->setIcon(QIcon(movie->currentPixmap()));
00151 }
00152 
00153 void KAnimatedButtonPrivate::_k_movieFinished()
00154 {
00155     // if not running, make it loop
00156     if (movie->state() == QMovie::NotRunning) {
00157         movie->start();
00158     }
00159 }
00160 
00161 void KAnimatedButton::updateIcons()
00162 {
00163     const int icon_size = iconDimensions();
00164     d->pixmap = QPixmap();
00165     QMovie *movie = KIconLoader::global()->loadMovie(d->icon_name, KIconLoader::NoGroup, -icon_size);
00166     if (movie) {
00167         d->frames = 0;
00168         movie->setCacheMode(QMovie::CacheAll);
00169         connect(movie, SIGNAL(frameChanged(int)), this, SLOT(_k_movieFrameChanged(int)));
00170         connect(movie, SIGNAL(finished()), this, SLOT(_k_movieFinished()));
00171     } else {
00172         const QString path = KIconLoader::global()->iconPath(d->icon_name, -icon_size);
00173         QImage img(path);
00174         if (img.isNull())
00175             return;
00176 
00177         if ((img.width() % icon_size != 0) || (img.height() % icon_size != 0))
00178             return;
00179 
00180         d->frames = (img.height() / icon_size) * (img.width() / icon_size);
00181         d->pixmap = QPixmap::fromImage(img);
00182     }
00183 
00184     d->current_frame = 0;
00185     qDeleteAll(d->framesCache);
00186     d->framesCache.fill(0);
00187     d->framesCache.resize(d->frames);
00188     delete d->movie;
00189     d->movie = movie;
00190 
00191     if (d->movie) {
00192         d->movie->jumpToFrame(0);
00193         d->_k_movieFrameChanged(0);
00194     } else {
00195         d->updateCurrentIcon();
00196     }
00197 }
00198 
00199 int KAnimatedButton::iconDimensions() const
00200 {
00201   return qMin(iconSize().width(), iconSize().height());
00202 }
00203 
00204 #include "kanimatedbutton.moc"

KDEUI

Skip menu "KDEUI"
  • Main Page
  • Modules
  • Namespace List
  • Class Hierarchy
  • Alphabetical List
  • Class List
  • File List
  • Namespace Members
  • Class Members
  • Related Pages

kdelibs

Skip menu "kdelibs"
  • DNSSD
  • Interfaces
  •   KHexEdit
  •   KMediaPlayer
  •   KSpeech
  •   KTextEditor
  • Kate
  • kconf_update
  • KDE3Support
  •   KUnitTest
  • KDECore
  • KDED
  • KDEsu
  • KDEUI
  • KDocTools
  • KFile
  • KHTML
  • KImgIO
  • KInit
  • kio
  • KIOSlave
  • KJS
  •   KJS-API
  •   WTF
  • kjsembed
  • KNewStuff
  • KParts
  • KPty
  • Kross
  • KUtils
  • Nepomuk
  • Plasma
  • Solid
  • Sonnet
  • ThreadWeaver
Generated for kdelibs by doxygen 1.6.1
This website is maintained by Adriaan de Groot and Allen Winter.
KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal