~ubuntu-branches/ubuntu/quantal/kpackagekit/quantal

« back to all changes in this revision

Viewing changes to AddRm/KpkPackageDetails.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Rohan Garg
  • Date: 2011-01-10 17:20:02 UTC
  • mfrom: (1.2.13 upstream)
  • Revision ID: james.westby@ubuntu.com-20110110172002-64acog2s0tk4iav9
Tags: 0.6.3.3-0ubuntu1
* New upstream release
  - Refresh kubuntu_06_no_automatic_updates.diff
  - Drop kubuntu_08_updates_info.diff, applied upstream

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/***************************************************************************
2
 
 *   Copyright (C) 2009-2010 by Daniel Nicoletti                           *
3
 
 *   dantti85-pk@yahoo.com.br                                              *
4
 
 *                                                                         *
5
 
 *   This program is free software; you can redistribute it and/or modify  *
6
 
 *   it under the terms of the GNU General Public License as published by  *
7
 
 *   the Free Software Foundation; either version 2 of the License, or     *
8
 
 *   (at your option) any later version.                                   *
9
 
 *                                                                         *
10
 
 *   This program is distributed in the hope that it will be useful,       *
11
 
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
12
 
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
13
 
 *   GNU General Public License for more details.                          *
14
 
 *                                                                         *
15
 
 *   You should have received a copy of the GNU General Public License     *
16
 
 *   along with this program; see the file COPYING. If not, write to       *
17
 
 *   the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,  *
18
 
 *   Boston, MA 02110-1301, USA.                                           *
19
 
 ***************************************************************************/
20
 
 
21
 
#include "KpkPackageDetails.h"
22
 
 
23
 
#include "ScreenShotViewer.h"
24
 
 
25
 
#include <KpkPackageModel.h>
26
 
#include <KpkSimplePackageModel.h>
27
 
#include <KpkStrings.h>
28
 
#include <KpkIcons.h>
29
 
#include <AppInstall.h>
30
 
 
31
 
#include <KMessageBox>
32
 
 
33
 
#include <KService>
34
 
#include <KServiceGroup>
35
 
#include <KDesktopFile>
36
 
#include <KTemporaryFile>
37
 
#include <KPixmapSequence>
38
 
#include <QTextDocument>
39
 
#include <QPlainTextEdit>
40
 
#include <QPainter>
41
 
 
42
 
#include <KIO/Job>
43
 
#include <KMenu>
44
 
 
45
 
#include <KDebug>
46
 
 
47
 
#include "GraphicsOpacityDropShadowEffect.h"
48
 
 
49
 
#define BLUR_RADIUS 15
50
 
#define FINAL_HEIGHT 210
51
 
 
52
 
Q_DECLARE_METATYPE(KPixmapSequenceOverlayPainter**)
53
 
 
54
 
KpkPackageDetails::KpkPackageDetails(QWidget *parent)
55
 
 : QWidget(parent),
56
 
   m_busySeq(0),
57
 
   m_display(false),
58
 
   m_hideVersion(false),
59
 
   m_transaction(0),
60
 
   m_hasDetails(false),
61
 
   m_hasFileList(false),
62
 
   m_dependsModel(0),
63
 
   m_requiresModel(0)
64
 
{
65
 
    setupUi(this);
66
 
 
67
 
    Enum::Roles roles = Client::instance()->actions();
68
 
    // Create a stacked layout to put the views in
69
 
    m_viewLayout = new QStackedLayout(stackedWidget);
70
 
 
71
 
    KMenu *menu = new KMenu(i18n("Display"), this);
72
 
    m_actionGroup = new QActionGroup(this);
73
 
    QAction *action = 0;
74
 
 
75
 
    // we check to see which roles are supported by the backend
76
 
    // if so we ask for information and create the containers
77
 
    if (roles & Enum::RoleGetDetails) {
78
 
        action = menu->addAction(i18n("Description"));
79
 
        action->setCheckable(true);
80
 
        action->setData(Enum::RoleGetDetails);
81
 
        m_actionGroup->addAction(action);
82
 
        m_viewLayout->addWidget(descriptionW);
83
 
        descriptionW->setWidgetResizable(true);
84
 
    }
85
 
 
86
 
    if (roles & Enum::RoleGetDepends) {
87
 
        action = menu->addAction(i18n("Depends On"));
88
 
        action->setCheckable(true);
89
 
        action->setData(Enum::RoleGetDepends);
90
 
        m_actionGroup->addAction(action);
91
 
        dependsOnLV = new QListView(stackedWidget);
92
 
        dependsOnLV->setFrameShape(QFrame::NoFrame);
93
 
        // Sets a transparent background
94
 
        QWidget *actionsViewport = dependsOnLV->viewport();
95
 
        QPalette palette = actionsViewport->palette();
96
 
        palette.setColor(actionsViewport->backgroundRole(), Qt::transparent);
97
 
        palette.setColor(actionsViewport->foregroundRole(), palette.color(QPalette::WindowText));
98
 
        actionsViewport->setPalette(palette);
99
 
        m_viewLayout->addWidget(dependsOnLV);
100
 
    }
101
 
 
102
 
    if (roles & Enum::RoleGetRequires) {
103
 
        action = menu->addAction(i18n("Required By"));
104
 
        action->setCheckable(true);
105
 
        action->setData(Enum::RoleGetRequires);
106
 
        m_actionGroup->addAction(action);
107
 
        requiredByLV = new QListView(stackedWidget);
108
 
        requiredByLV->setFrameShape(QFrame::NoFrame);
109
 
        // Sets a transparent background
110
 
        QWidget *actionsViewport = requiredByLV->viewport();
111
 
        QPalette palette = actionsViewport->palette();
112
 
        palette.setColor(actionsViewport->backgroundRole(), Qt::transparent);
113
 
        palette.setColor(actionsViewport->foregroundRole(), palette.color(QPalette::WindowText));
114
 
        actionsViewport->setPalette(palette);
115
 
        m_viewLayout->addWidget(requiredByLV);
116
 
    }
117
 
 
118
 
    if (roles & Enum::RoleGetFiles) {
119
 
        action = menu->addAction(i18n("File List"));
120
 
        action->setCheckable(true);
121
 
        action->setData(Enum::RoleGetFiles);
122
 
        m_actionGroup->addAction(action);
123
 
        filesPTE = new QPlainTextEdit(stackedWidget);
124
 
        filesPTE->setFrameShape(QFrame::NoFrame);
125
 
        filesPTE->setReadOnly(true);
126
 
        // Sets a transparent background
127
 
        QWidget *actionsViewport = filesPTE->viewport();
128
 
        QPalette palette = actionsViewport->palette();
129
 
        palette.setColor(actionsViewport->backgroundRole(), Qt::transparent);
130
 
        palette.setColor(actionsViewport->foregroundRole(), palette.color(QPalette::WindowText));
131
 
        actionsViewport->setPalette(palette);
132
 
        m_viewLayout->addWidget(filesPTE);
133
 
    }
134
 
 
135
 
    // Check to se if we have any action
136
 
    if (m_actionGroup->actions().isEmpty()) {
137
 
        menuTB->hide();
138
 
    } else {
139
 
        action = m_actionGroup->actions().first();
140
 
        action->setChecked(true);
141
 
        connect(m_actionGroup, SIGNAL(triggered(QAction *)),
142
 
                this, SLOT(actionActivated(QAction *)));
143
 
        // Set the menu
144
 
        menuTB->setMenu(menu);
145
 
        menuTB->setIcon(KIcon("help-about"));
146
 
    }
147
 
 
148
 
    m_busySeq = new KPixmapSequenceOverlayPainter(this);
149
 
    m_busySeq->setSequence(KPixmapSequence("process-working", KIconLoader::SizeSmallMedium));
150
 
    m_busySeq->setAlignment(Qt::AlignHCenter | Qt::AlignVCenter);
151
 
    m_busySeq->setWidget(stackedWidget);
152
 
 
153
 
    // Setup the opacit effect that makes the descriptio transparent
154
 
    // after finished it checks in display() to see if it shouldn't show
155
 
    // up again. The property animation is always the same, the only different thing
156
 
    // is the the Forward or Backward property
157
 
    QGraphicsOpacityEffect *effect = new QGraphicsOpacityEffect(stackedWidget);
158
 
    effect->setOpacity(0);
159
 
//     stackedWidget->setVisible(false);
160
 
    stackedWidget->setGraphicsEffect(effect);
161
 
    m_fadeStacked = new QPropertyAnimation(effect, "opacity");
162
 
    m_fadeStacked->setDuration(500);
163
 
    m_fadeStacked->setStartValue(qreal(0));
164
 
    m_fadeStacked->setEndValue(qreal(1));
165
 
    connect(m_fadeStacked, SIGNAL(finished()), this, SLOT(display()));
166
 
 
167
 
 
168
 
    // It's is impossible due to some limitation in Qt to set two effects on the same
169
 
    // Widget
170
 
    m_fadeScreenshot = new QPropertyAnimation(effect, "opacity");
171
 
    GraphicsOpacityDropShadowEffect *shadow = new GraphicsOpacityDropShadowEffect(screenshotL);
172
 
    shadow->setOpacity(0);
173
 
    shadow->setBlurRadius(BLUR_RADIUS);
174
 
    shadow->setOffset(2);
175
 
    shadow->setColor(QApplication::palette().dark().color());
176
 
    screenshotL->setGraphicsEffect(shadow);
177
 
 
178
 
    m_fadeScreenshot = new QPropertyAnimation(shadow, "opacity");
179
 
    m_fadeScreenshot->setDuration(500);
180
 
    m_fadeScreenshot->setStartValue(qreal(0));
181
 
    m_fadeScreenshot->setEndValue(qreal(1));
182
 
    connect(m_fadeScreenshot, SIGNAL(finished()), this, SLOT(display()));
183
 
 
184
 
    // This pannel expanding
185
 
    QPropertyAnimation *anim1 = new QPropertyAnimation(this, "maximumSize");
186
 
    anim1->setDuration(500);
187
 
    anim1->setEasingCurve(QEasingCurve::OutQuart);
188
 
    anim1->setStartValue(QSize(QWIDGETSIZE_MAX, 0));
189
 
    anim1->setEndValue(QSize(QWIDGETSIZE_MAX, FINAL_HEIGHT));
190
 
    QPropertyAnimation *anim2 = new QPropertyAnimation(this, "minimumSize");
191
 
    anim2->setDuration(500);
192
 
    anim2->setEasingCurve(QEasingCurve::OutQuart);
193
 
    anim2->setStartValue(QSize(QWIDGETSIZE_MAX, 0));
194
 
    anim2->setEndValue(QSize(QWIDGETSIZE_MAX, FINAL_HEIGHT));
195
 
 
196
 
    m_expandPanel = new QParallelAnimationGroup;
197
 
    m_expandPanel->addAnimation(anim1);
198
 
    m_expandPanel->addAnimation(anim2);
199
 
    connect(m_expandPanel, SIGNAL(finished()), this, SLOT(display()));
200
 
}
201
 
 
202
 
KpkPackageDetails::~KpkPackageDetails()
203
 
{
204
 
}
205
 
 
206
 
void KpkPackageDetails::setPackage(const QModelIndex &index)
207
 
{
208
 
    QString pkgId = index.data(KpkPackageModel::IdRole).toString();
209
 
    QString appId = index.data(KpkPackageModel::ApplicationId).toString();
210
 
 
211
 
    // if it's the same package and the same application, return
212
 
    if (pkgId == m_packageId && appId == m_appId) {
213
 
        return;
214
 
    } else if (maximumSize().height() == 0) {
215
 
        // Expand the panel
216
 
        m_display = true;
217
 
        m_expandPanel->setDirection(QAbstractAnimation::Forward);
218
 
        m_expandPanel->start();
219
 
    } else {
220
 
        // Hide the old description
221
 
        fadeOut(KpkPackageDetails::FadeScreenshot | KpkPackageDetails::FadeStacked);
222
 
    }
223
 
 
224
 
    m_packageId = pkgId;
225
 
    m_appId     = appId;
226
 
    Enum::Info info = static_cast<Enum::Info>(index.data(KpkPackageModel::InfoRole).toUInt());
227
 
 
228
 
    m_package       = QSharedPointer<Package>(new Package(m_packageId, info, QString()));;
229
 
    m_hasDetails    = false;
230
 
    m_hasFileList   = false;
231
 
    m_hasRequires   = false;
232
 
    m_hasDepends    = false;
233
 
 
234
 
    QString pkgIconPath = index.data(KpkPackageModel::IconRole).toString();
235
 
    m_currentIcon       = KpkIcons::getIcon(pkgIconPath, QString()).pixmap(64, 64);
236
 
    m_appName           = index.data(KpkPackageModel::NameRole).toString();
237
 
 
238
 
    m_currentScreenshot = AppInstall::instance()->thumbnail(m_package->name());
239
 
    if (!m_currentScreenshot.isEmpty()) {
240
 
        if (m_screenshotPath.contains(m_currentScreenshot)) {
241
 
            display();
242
 
        } else {
243
 
            KTemporaryFile *tempFile = new KTemporaryFile;
244
 
            tempFile->setPrefix("appget");
245
 
            tempFile->setSuffix(".png");
246
 
            tempFile->open();
247
 
            KIO::FileCopyJob *job = KIO::file_copy(m_currentScreenshot,
248
 
                                                   tempFile->fileName(),
249
 
                                                   -1,
250
 
                                                   KIO::Overwrite | KIO::HideProgressInfo);
251
 
            connect(job, SIGNAL(result(KJob *)),
252
 
                    this, SLOT(resultJob(KJob *)));
253
 
        }
254
 
    }
255
 
 
256
 
    if (m_actionGroup->checkedAction()) {
257
 
        actionActivated(m_actionGroup->checkedAction());
258
 
    }
259
 
}
260
 
 
261
 
void KpkPackageDetails::on_screenshotL_clicked()
262
 
{
263
 
    QString screenshot;
264
 
    screenshot = AppInstall::instance()->screenshot(m_package->name());
265
 
    if (screenshot.isEmpty()) {
266
 
        return;
267
 
    }
268
 
    ScreenShotViewer *view = new ScreenShotViewer(screenshot);
269
 
    view->setWindowTitle(m_appName);
270
 
    view->show();
271
 
}
272
 
 
273
 
void KpkPackageDetails::hidePackageVersion(bool hide)
274
 
{
275
 
    m_hideVersion = hide;
276
 
}
277
 
 
278
 
void KpkPackageDetails::actionActivated(QAction *action)
279
 
{
280
 
    // don't fade the screenshot
281
 
    // if the package changed setPackage() fades both
282
 
    fadeOut(FadeStacked);
283
 
 
284
 
    // disconnect the transaction
285
 
    // so that we don't get old data
286
 
    if (m_transaction) {
287
 
        disconnect(m_transaction, SIGNAL(details(const QSharedPointer<PackageKit::Package> &)),
288
 
                   this, SLOT(description(const QSharedPointer<PackageKit::Package> &)));
289
 
        disconnect(m_transaction, SIGNAL(package(const QSharedPointer<PackageKit::Package> &)),
290
 
                   m_dependsModel, SLOT(addPackage(const QSharedPointer<PackageKit::Package> &)));
291
 
        disconnect(m_transaction, SIGNAL(package(const QSharedPointer<PackageKit::Package> &)),
292
 
                   m_requiresModel, SLOT(addPackage(const QSharedPointer<PackageKit::Package> &)));
293
 
        disconnect(m_transaction, SIGNAL(files(const QSharedPointer<PackageKit::Package> &, const QStringList &)),
294
 
                   this, SLOT(files(const QSharedPointer<PackageKit::Package> &, const QStringList &)));
295
 
        disconnect(m_transaction, SIGNAL(finished(PackageKit::Enum::Exit, uint)),
296
 
                   this, SLOT(finished()));
297
 
        m_transaction = 0;
298
 
    }
299
 
 
300
 
    // Check to see if we don't already have the required data
301
 
    uint role = action->data().toUInt();
302
 
    if (role == Enum::RoleGetDetails &&
303
 
        m_package->hasDetails()) {
304
 
        description(m_package);
305
 
        return;
306
 
    }
307
 
    switch (role) {
308
 
    case Enum::RoleGetDetails:
309
 
        if (m_package->hasDetails()) {
310
 
            description(m_package);
311
 
            return;
312
 
        }
313
 
        break;
314
 
    case Enum::RoleGetDepends:
315
 
        if (m_hasDepends) {
316
 
            display();
317
 
            return;
318
 
        }
319
 
        break;
320
 
    case Enum::RoleGetRequires:
321
 
        if (m_hasRequires) {
322
 
            display();
323
 
            return;
324
 
        }
325
 
        break;
326
 
    case Enum::RoleGetFiles:
327
 
        if (m_hasFileList) {
328
 
            display();
329
 
            return;
330
 
        }
331
 
        break;
332
 
    }
333
 
 
334
 
    // we don't have the data
335
 
    m_transaction = new Transaction(QString());
336
 
    connect(m_transaction, SIGNAL(finished(PackageKit::Enum::Exit, uint)),
337
 
            this, SLOT(finished()));
338
 
    switch (role) {
339
 
    case Enum::RoleGetDetails:
340
 
        connect(m_transaction, SIGNAL(details(const QSharedPointer<PackageKit::Package> &)),
341
 
                this, SLOT(description(const QSharedPointer<PackageKit::Package> &)));
342
 
        m_transaction->getDetails(m_package);
343
 
        break;
344
 
    case Enum::RoleGetDepends:
345
 
        if (m_dependsModel) {
346
 
            delete m_dependsModel;
347
 
        }
348
 
        m_dependsModel = new KpkSimplePackageModel(this);
349
 
        connect(m_transaction, SIGNAL(package(const QSharedPointer<PackageKit::Package> &)),
350
 
                m_dependsModel, SLOT(addPackage(const QSharedPointer<PackageKit::Package> &)));
351
 
        m_transaction->getDepends(m_package, PackageKit::Enum::NoFilter, false);
352
 
        break;
353
 
    case Enum::RoleGetRequires:
354
 
        if (m_requiresModel) {
355
 
            delete m_requiresModel;
356
 
        }
357
 
        m_requiresModel = new KpkSimplePackageModel(this);
358
 
        connect(m_transaction, SIGNAL(package(const QSharedPointer<PackageKit::Package> &)),
359
 
                m_requiresModel, SLOT(addPackage(const QSharedPointer<PackageKit::Package> &)));
360
 
        m_transaction->getRequires(m_package, PackageKit::Enum::NoFilter, false);
361
 
        break;
362
 
    case Enum::RoleGetFiles:
363
 
        connect(m_transaction, SIGNAL(files(const QSharedPointer<PackageKit::Package> &, const QStringList &)),
364
 
                this, SLOT(files(const QSharedPointer<PackageKit::Package> &, const QStringList &)));
365
 
        m_transaction->getFiles(m_package);
366
 
        break;
367
 
    }
368
 
 
369
 
    if (m_transaction->error()) {
370
 
        KMessageBox::sorry(this, KpkStrings::daemonError(m_transaction->error()));
371
 
    } else {
372
 
        m_busySeq->start();
373
 
    }
374
 
}
375
 
 
376
 
void KpkPackageDetails::resultJob(KJob *job)
377
 
{
378
 
    kDebug();
379
 
    KIO::FileCopyJob *fJob = qobject_cast<KIO::FileCopyJob*>(job);
380
 
    if (!fJob->error()) {
381
 
        m_screenshotPath[fJob->srcUrl().url()] = fJob->destUrl().toLocalFile();
382
 
        display();
383
 
    }
384
 
}
385
 
 
386
 
void KpkPackageDetails::hide()
387
 
{
388
 
    m_display = false;
389
 
    // Clean the old description otherwise if the user selects the same
390
 
    // package the pannel won't expand
391
 
    m_packageId.clear();
392
 
    m_appId.clear();
393
 
 
394
 
    if (maximumSize().height() == FINAL_HEIGHT) {
395
 
        if (m_fadeStacked->currentValue().toReal() == 0 &&
396
 
            m_fadeScreenshot->currentValue().toReal() == 0) {
397
 
            // Screen shot and description faded let's shrink the pannel
398
 
            m_expandPanel->setDirection(QAbstractAnimation::Backward);
399
 
            m_expandPanel->start();
400
 
        } else {
401
 
            // Hide current description
402
 
            fadeOut(KpkPackageDetails::FadeScreenshot | KpkPackageDetails::FadeStacked);
403
 
        }
404
 
    }
405
 
}
406
 
 
407
 
void KpkPackageDetails::fadeOut(FadeWidgets widgets)
408
 
{
409
 
    // Fade out only if needed
410
 
    if ((widgets & FadeStacked) && m_fadeStacked->currentValue().toReal() != 0) {
411
 
        m_fadeStacked->setDirection(QAbstractAnimation::Backward);
412
 
        m_fadeStacked->start();
413
 
    }
414
 
 
415
 
    // Fade out the screenshot only if needed
416
 
    if ((widgets & FadeScreenshot) && m_fadeScreenshot->currentValue().toReal() != 0) {
417
 
        screenshotL->unsetCursor();
418
 
        m_fadeScreenshot->setDirection(QAbstractAnimation::Backward);
419
 
        m_fadeScreenshot->start();
420
 
    }
421
 
}
422
 
 
423
 
void KpkPackageDetails::display()
424
 
{
425
 
    // If we shouldn't be showing hide the pannel
426
 
    if (!m_display) {
427
 
        hide();
428
 
    } else if (maximumSize().height() == FINAL_HEIGHT) {
429
 
        // Check to see if the stacked widget is transparent
430
 
        if (m_fadeStacked->currentValue().toReal() == 0 &&
431
 
            m_actionGroup->checkedAction())
432
 
        {
433
 
            bool fadeIn = false;
434
 
            switch (m_actionGroup->checkedAction()->data().toUInt()) {
435
 
            case Enum::RoleGetDetails:
436
 
                if (m_hasDetails) {
437
 
                    setupDescription();
438
 
                    fadeIn = true;
439
 
                }
440
 
                break;
441
 
            case Enum::RoleGetDepends:
442
 
                if (m_hasDepends) {
443
 
                    QAbstractItemModel *currentModel = dependsOnLV->model();
444
 
                    if (currentModel != m_dependsModel) {
445
 
                        dependsOnLV->setModel(m_dependsModel);
446
 
                        delete currentModel;
447
 
                    }
448
 
                    if (m_viewLayout->currentWidget() != dependsOnLV) {
449
 
                        m_viewLayout->setCurrentWidget(dependsOnLV);
450
 
                    }
451
 
                    fadeIn = true;
452
 
                }
453
 
                break;
454
 
            case Enum::RoleGetRequires:
455
 
                if (m_hasRequires) {
456
 
                    QAbstractItemModel *currentModel = requiredByLV->model();
457
 
                    if (currentModel != m_requiresModel) {
458
 
                        requiredByLV->setModel(m_requiresModel);
459
 
                        delete currentModel;
460
 
                    }
461
 
                    if (m_viewLayout->currentWidget() != requiredByLV) {
462
 
                        m_viewLayout->setCurrentWidget(requiredByLV);
463
 
                    }
464
 
                    fadeIn = true;
465
 
                }
466
 
                break;
467
 
            case Enum::RoleGetFiles:
468
 
                if (m_hasFileList) {
469
 
                    filesPTE->clear();
470
 
                    if (m_currentFileList.isEmpty()) {
471
 
                        filesPTE->appendPlainText(i18n("No files were found."));
472
 
                    } else {
473
 
                        filesPTE->insertPlainText(m_currentFileList.join("\n"));
474
 
                    }
475
 
 
476
 
                    if (m_viewLayout->currentWidget() != filesPTE) {
477
 
                        m_viewLayout->setCurrentWidget(filesPTE);
478
 
                    }
479
 
                    fadeIn = true;
480
 
                }
481
 
                break;
482
 
            }
483
 
 
484
 
            if (fadeIn) {
485
 
                // Fade In
486
 
                m_fadeStacked->setDirection(QAbstractAnimation::Forward);
487
 
                m_fadeStacked->start();
488
 
            }
489
 
        }
490
 
 
491
 
        // Check to see if we have a screen shot and if we are
492
 
        // transparent, and make sure the details are going
493
 
        // to be shown
494
 
        if (m_fadeScreenshot->currentValue().toReal() == 0 &&
495
 
            m_screenshotPath.contains(m_currentScreenshot) &&
496
 
            m_fadeStacked->direction() == QAbstractAnimation::Forward) {
497
 
            QPixmap pixmap;
498
 
            pixmap = QPixmap(m_screenshotPath[m_currentScreenshot])
499
 
                             .scaled(160,120, Qt::KeepAspectRatio, Qt::SmoothTransformation);
500
 
            screenshotL->setPixmap(pixmap);
501
 
            screenshotL->setCursor(Qt::PointingHandCursor);
502
 
            // Fade In
503
 
            m_fadeScreenshot->setDirection(QAbstractAnimation::Forward);
504
 
            m_fadeScreenshot->start();
505
 
        }
506
 
    }
507
 
}
508
 
 
509
 
void KpkPackageDetails::setupDescription()
510
 
{
511
 
    if (m_viewLayout->currentWidget() != descriptionW) {
512
 
        m_viewLayout->setCurrentWidget(descriptionW);
513
 
    }
514
 
 
515
 
    //format and show description
516
 
    Package::Details *details = m_package->details();
517
 
 
518
 
    if (!details->description().isEmpty()) {
519
 
        descriptionL->setText(details->description().replace('\n', "<br>"));
520
 
        descriptionL->show();
521
 
    } else {
522
 
        descriptionL->clear();
523
 
    }
524
 
 
525
 
    if (!details->url().isEmpty()) {
526
 
        homepageL->setText("<a href=\"" + details->url() + "\">" +
527
 
                           details->url() + "</a>");
528
 
        homepageL->show();
529
 
    } else {
530
 
        homepageL->hide();
531
 
    }
532
 
 
533
 
    if (!details->license().isEmpty() && details->license() != "unknown") {
534
 
        // We have a license, check if we have and should show show package version
535
 
        if (!m_hideVersion && !m_package->version().isEmpty()) {
536
 
            licenseL->setText(m_package->version() + " - " + details->license());
537
 
        } else {
538
 
            licenseL->setText(details->license());
539
 
        }
540
 
        licenseL->show();
541
 
    } else if (!m_hideVersion) {
542
 
        licenseL->setText(m_package->version());
543
 
        licenseL->show();
544
 
    } else {
545
 
        licenseL->hide();
546
 
    }
547
 
 
548
 
    // Let's try to find the application's path in human user
549
 
    // readable easiest form :D
550
 
    KService::Ptr service = KService::serviceByDesktopName(m_appId);
551
 
    QVector<QPair<QString, QString> > ret;
552
 
    if (service) {
553
 
        ret = locateApplication(QString(), service->menuId());
554
 
    }
555
 
    if (ret.isEmpty()) {
556
 
        pathL->hide();
557
 
    } else {
558
 
        QString path;
559
 
        path.append(QString("<img width=\"16\" heigh=\"16\"src=\"%1\"/>")
560
 
                    .arg(KIconLoader::global()->iconPath("kde", KIconLoader::Small)));
561
 
        path.append(QString("&nbsp;%1 <img width=\"16\" heigh=\"16\" src=\"%2\"/>&nbsp;%3")
562
 
                    .arg(QString::fromUtf8("➜"))
563
 
                    .arg(KIconLoader::global()->iconPath("applications-other", KIconLoader::Small))
564
 
                    .arg(i18n("Applications")));
565
 
        for (int i = 0; i < ret.size(); i++) {
566
 
            path.append(QString("&nbsp;%1&nbsp;<img width=\"16\" heigh=\"16\" src=\"%2\"/>&nbsp;%3")
567
 
                        .arg(QString::fromUtf8("➜"))
568
 
                        .arg(KIconLoader::global()->iconPath(ret.at(i).second, KIconLoader::Small))
569
 
                        .arg(ret.at(i).first));
570
 
        }
571
 
        pathL->setText(path);
572
 
        pathL->show();
573
 
    }
574
 
 
575
 
//     if (details->group() != Enum::UnknownGroup) {
576
 
// //         description += "<tr><td align=\"right\"><b>" + i18nc("Group of the package", "Group") + ":</b></td><td>"
577
 
// //                     + KpkStrings::groups(details->group())
578
 
// //                     + "</td></tr>";
579
 
//     }
580
 
 
581
 
    if (details->size() > 0) {
582
 
        sizeL->setText(KGlobal::locale()->formatByteSize(details->size()));
583
 
        sizeL->show();
584
 
    } else {
585
 
        sizeL->hide();
586
 
    }
587
 
 
588
 
    if (m_currentIcon.isNull()) {
589
 
        iconL->clear();
590
 
    } else {
591
 
        iconL->setPixmap(m_currentIcon);
592
 
    }
593
 
}
594
 
 
595
 
QVector<QPair<QString, QString> > KpkPackageDetails::locateApplication(const QString &_relPath, const QString &menuId) const
596
 
{
597
 
    QVector<QPair<QString, QString> > ret;
598
 
    KServiceGroup::Ptr root = KServiceGroup::group(_relPath);
599
 
 
600
 
    if (!root || !root->isValid()) {
601
 
        return ret;
602
 
    }
603
 
 
604
 
    const KServiceGroup::List list = root->entries(false /* sorted */,
605
 
                                                   true /* exclude no display entries */,
606
 
                                                   false /* allow separators */);
607
 
 
608
 
    for (KServiceGroup::List::ConstIterator it = list.constBegin(); it != list.constEnd(); ++it) {
609
 
        const KSycocaEntry::Ptr p = (*it);
610
 
 
611
 
        if (p->isType(KST_KService)) {
612
 
            const KService::Ptr service = KService::Ptr::staticCast(p);
613
 
 
614
 
            if (service->noDisplay()) {
615
 
                continue;
616
 
            }
617
 
 
618
 
//             kDebug() << menuId << service->menuId();
619
 
            if (service->menuId() == menuId) {
620
 
                QPair<QString, QString> pair;
621
 
                pair.first  = service->name();
622
 
                pair.second = service->icon();
623
 
                ret << pair;
624
 
//                 kDebug() << "FOUND!";
625
 
                return ret;
626
 
            }
627
 
        } else if (p->isType(KST_KServiceGroup)) {
628
 
            const KServiceGroup::Ptr serviceGroup = KServiceGroup::Ptr::staticCast(p);
629
 
 
630
 
            if (serviceGroup->noDisplay() || serviceGroup->childCount() == 0) {
631
 
                continue;
632
 
            }
633
 
 
634
 
            QVector<QPair<QString, QString> > found;
635
 
            found = locateApplication(serviceGroup->relPath(), menuId);
636
 
            if (!found.isEmpty()) {
637
 
                QPair<QString, QString> pair;
638
 
                pair.first  = serviceGroup->caption();
639
 
                pair.second = serviceGroup->icon();
640
 
                ret << pair;
641
 
                ret << found;
642
 
                return ret;
643
 
            }
644
 
        } else {
645
 
            kWarning(250) << "KServiceGroup: Unexpected object in list!";
646
 
            continue;
647
 
        }
648
 
    }
649
 
 
650
 
    return ret;
651
 
}
652
 
 
653
 
void KpkPackageDetails::description(const QSharedPointer<PackageKit::Package> &package)
654
 
{
655
 
    m_package = package;
656
 
}
657
 
 
658
 
void KpkPackageDetails::finished()
659
 
{
660
 
    if (m_busySeq) {
661
 
        m_busySeq->stop();
662
 
    }
663
 
    m_transaction = 0;
664
 
 
665
 
    Transaction *transaction = qobject_cast<Transaction*>(sender());
666
 
    if (transaction) {
667
 
        if (transaction->role() == Enum::RoleGetDetails) {
668
 
            m_hasDetails  = true;
669
 
        } else if (transaction->role() == Enum::RoleGetFiles) {
670
 
            m_hasFileList = true;
671
 
        } else if (transaction->role() == Enum::RoleGetRequires) {
672
 
            m_hasRequires = true;
673
 
        } else if (transaction->role() == Enum::RoleGetDepends) {
674
 
            m_hasDepends  = true;
675
 
        } else {
676
 
            return;
677
 
        }
678
 
 
679
 
        display();
680
 
    }
681
 
}
682
 
 
683
 
void KpkPackageDetails::files(QSharedPointer<PackageKit::Package> package, const QStringList &files)
684
 
{
685
 
    Q_UNUSED(package)
686
 
 
687
 
    m_currentFileList = files;
688
 
}
689
 
 
690
 
 
691
 
#include "KpkPackageDetails.moc"