File indexing completed on 2025-03-09 03:52:09
0001 /* ============================================================ 0002 * 0003 * This file is a part of digiKam project 0004 * https://www.digikam.org 0005 * 0006 * Date : 2003-02-16 0007 * Description : a presentation tool. 0008 * 0009 * SPDX-FileCopyrightText: 2006-2009 by Valerio Fuoglio <valerio dot fuoglio at gmail dot com> 0010 * SPDX-FileCopyrightText: 2009 by Andi Clemens <andi dot clemens at googlemail dot com> 0011 * SPDX-FileCopyrightText: 2003-2005 by Renchi Raju <renchi dot raju at gmail dot com> 0012 * SPDX-FileCopyrightText: 2012-2024 by Gilles Caulier <caulier dot gilles at gmail dot com> 0013 * SPDX-FileCopyrightText: 2021 by Phuoc Khanh Le <phuockhanhnk94 at gmail dot com> 0014 * 0015 * SPDX-License-Identifier: GPL-2.0-or-later 0016 * 0017 * ============================================================ */ 0018 0019 #include "presentationwidget.h" 0020 0021 // C++ includes 0022 0023 #include <cmath> 0024 #include <cstdlib> 0025 #include <ctime> 0026 0027 // Qt includes 0028 0029 #include <QCursor> 0030 #include <QFont> 0031 #include <QKeyEvent> 0032 #include <QMouseEvent> 0033 #include <QPainter> 0034 #include <QPainterPath> 0035 #include <QTimer> 0036 #include <QWheelEvent> 0037 #include <QApplication> 0038 #include <QScreen> 0039 #include <QWindow> 0040 0041 #include <QDebug> 0042 0043 // KDE includes 0044 0045 #include <klocalizedstring.h> 0046 0047 // Local includes 0048 0049 #include "digikam_config.h" 0050 #include "presentationcontainer.h" 0051 #include "presentationctrlwidget.h" 0052 #include "presentationloader.h" 0053 #include "presentation_mainpage.h" 0054 0055 #ifdef HAVE_MEDIAPLAYER 0056 # include "presentationaudiowidget.h" 0057 # include "slidevideo.h" 0058 #endif 0059 0060 using namespace Digikam; 0061 0062 namespace DigikamGenericPresentationPlugin 0063 { 0064 0065 class Q_DECL_HIDDEN PresentationWidget::Private 0066 { 0067 0068 public: 0069 0070 explicit Private() 0071 : sharedData (nullptr), 0072 imageLoader (nullptr), 0073 0074 #ifdef HAVE_MEDIAPLAYER 0075 0076 playbackWidget (nullptr), 0077 videoView (nullptr), 0078 0079 #endif 0080 0081 timer (nullptr), 0082 fileIndex (0), 0083 effect (nullptr), 0084 effectRunning (false), 0085 x (0), 0086 y (0), 0087 w (0), 0088 h (0), 0089 dx (0), 0090 dy (0), 0091 ix (0), 0092 iy (0), 0093 i (0), 0094 j (0), 0095 subType (0), 0096 x0 (0), 0097 y0 (0), 0098 x1 (0), 0099 y1 (0), 0100 wait (0), 0101 fx (0), 0102 fy (0), 0103 alpha (0), 0104 fd (0), 0105 intArray (nullptr), 0106 pdone (0), 0107 pixelMatrix (nullptr), 0108 slideCtrlWidget (nullptr), 0109 mouseMoveTimer (nullptr), 0110 deskX (0), 0111 deskY (0), 0112 deskWidth (0), 0113 deskHeight (0) 0114 { 0115 } 0116 0117 PresentationContainer* sharedData; 0118 0119 // ------------------------- 0120 0121 QMap<QString, EffectMethod> Effects; 0122 0123 PresentationLoader* imageLoader; 0124 QPixmap currImage; 0125 0126 #ifdef HAVE_MEDIAPLAYER 0127 0128 PresentationAudioWidget* playbackWidget; 0129 SlideVideo* videoView; 0130 0131 #endif 0132 0133 QTimer* timer; 0134 int fileIndex; 0135 0136 EffectMethod effect; 0137 bool effectRunning; 0138 QString effectName; 0139 0140 /// values for state of various effects 0141 int x; 0142 int y; 0143 int w; 0144 int h; 0145 int dx; 0146 int dy; 0147 int ix; 0148 int iy; 0149 int i; 0150 int j; 0151 int subType; 0152 int x0; 0153 int y0; 0154 int x1; 0155 int y1; 0156 int wait; 0157 double fx; 0158 double fy; 0159 double alpha; 0160 double fd; 0161 int* intArray; 0162 bool pdone; 0163 bool** pixelMatrix; 0164 0165 /// static 0166 QPolygon pa; 0167 0168 PresentationCtrlWidget* slideCtrlWidget; 0169 QTimer* mouseMoveTimer; 0170 0171 int deskX; 0172 int deskY; 0173 int deskWidth; 0174 int deskHeight; 0175 }; 0176 0177 PresentationWidget::PresentationWidget(PresentationContainer* const sharedData) 0178 : QWidget(), 0179 d (new Private), 0180 randomGenerator(QRandomGenerator::global()) 0181 { 0182 setAttribute(Qt::WA_DeleteOnClose); 0183 setContextMenuPolicy(Qt::PreventContextMenu); 0184 0185 #ifdef Q_OS_WIN 0186 0187 setWindowFlags(Qt::Popup | 0188 Qt::FramelessWindowHint | 0189 Qt::WindowStaysOnTopHint); 0190 0191 #else 0192 0193 setWindowState(windowState() | Qt::WindowFullScreen); 0194 0195 #endif 0196 0197 QScreen* screen = qApp->primaryScreen(); 0198 0199 if (QWidget* const widget = qApp->activeWindow()) 0200 { 0201 if (QWindow* const window = widget->windowHandle()) 0202 { 0203 screen = window->screen(); 0204 } 0205 } 0206 0207 QRect deskRect = screen->geometry(); 0208 d->deskX = deskRect.x(); 0209 d->deskY = deskRect.y(); 0210 d->deskWidth = deskRect.width(); 0211 d->deskHeight = deskRect.height(); 0212 0213 move(d->deskX, d->deskY); 0214 resize(d->deskWidth, d->deskHeight); 0215 0216 d->sharedData = sharedData; 0217 d->sharedData->display = this; 0218 0219 d->slideCtrlWidget = new PresentationCtrlWidget(this, d->sharedData); 0220 d->slideCtrlWidget->hide(); 0221 0222 int w = d->slideCtrlWidget->width() - 1; 0223 d->slideCtrlWidget->move(d->deskX + d->deskWidth - w, d->deskY); 0224 0225 if (!d->sharedData->loop) 0226 { 0227 d->slideCtrlWidget->setEnabledPrev(false); 0228 } 0229 0230 connect(d->slideCtrlWidget, SIGNAL(signalPause()), 0231 this, SLOT(slotPause())); 0232 0233 connect(d->slideCtrlWidget, SIGNAL(signalPlay()), 0234 this, SLOT(slotPlay())); 0235 0236 connect(d->slideCtrlWidget, SIGNAL(signalNext()), 0237 this, SLOT(slotNext())); 0238 0239 connect(d->slideCtrlWidget, SIGNAL(signalPrev()), 0240 this, SLOT(slotPrev())); 0241 0242 connect(d->slideCtrlWidget, SIGNAL(signalClose()), 0243 this, SLOT(slotClose())); 0244 0245 connect(d->slideCtrlWidget, SIGNAL(signalRemoveImageFromList()), 0246 this, SLOT(slotRemoveImageFromList())); 0247 0248 #ifdef HAVE_MEDIAPLAYER 0249 0250 // -- playback widget ------------------------------- 0251 0252 d->playbackWidget = new PresentationAudioWidget(this, d->sharedData->soundtrackUrls, d->sharedData); 0253 d->playbackWidget->hide(); 0254 d->playbackWidget->move(d->deskX, d->deskY); 0255 0256 // -- video preview --------------------------------- 0257 0258 d->videoView = new SlideVideo(this); 0259 0260 // TODO: pass mouse events from d->videoView to this ? 0261 //d->videoView->installEventFilter(this); 0262 0263 connect(d->videoView, SIGNAL(signalVideoLoaded(bool)), 0264 this, SLOT(slotVideoLoaded(bool))); 0265 0266 connect(d->videoView, SIGNAL(signalVideoFinished()), 0267 this, SLOT(slotVideoFinished())); 0268 0269 d->videoView->hide(); 0270 d->videoView->resize(d->deskWidth, d->deskHeight); 0271 0272 #endif 0273 0274 // --------------------------------------------------------------- 0275 0276 d->fileIndex = -1; // start with -1 0277 d->effect = nullptr; 0278 d->effectRunning = false; 0279 d->intArray = nullptr; 0280 m_endOfShow = false; 0281 m_simplyShow = false; 0282 m_startPainter = false; 0283 m_firstPainter = true; 0284 d->timer = new QTimer(this); 0285 0286 connect(d->timer, SIGNAL(timeout()), 0287 this, SLOT(slotTimeOut())); 0288 0289 d->pa = QPolygon(4); 0290 m_buffer = QPixmap(size()); 0291 m_buffer.fill(Qt::black); 0292 0293 d->imageLoader = new PresentationLoader(d->sharedData, width(), height(), d->fileIndex); 0294 0295 // -------------------------------------------------- 0296 0297 registerEffects(); 0298 0299 if (d->sharedData->effectName == QLatin1String("Random")) 0300 { 0301 d->effect = getRandomEffect(); 0302 } 0303 else 0304 { 0305 d->effectName = d->sharedData->effectName; 0306 d->effect = d->Effects[d->sharedData->effectName]; 0307 0308 if (!d->effect) 0309 { 0310 d->effect = d->Effects[QLatin1String("None")]; 0311 d->effectName = QLatin1String("None"); 0312 } 0313 } 0314 0315 d->timer->setSingleShot(true); 0316 0317 if (d->sharedData->offAutoDelay) 0318 { 0319 d->timer->stop(); 0320 slotTimeOut(); 0321 } 0322 else 0323 { 0324 d->timer->start(500); 0325 } 0326 0327 // -- hide cursor when not moved -------------------- 0328 0329 d->mouseMoveTimer = new QTimer(this); 0330 d->mouseMoveTimer->setSingleShot(true); 0331 0332 connect(d->mouseMoveTimer, SIGNAL(timeout()), 0333 this, SLOT(slotMouseMoveTimeOut())); 0334 0335 setMouseTracking(true); 0336 slotMouseMoveTimeOut(); 0337 0338 #ifdef HAVE_MEDIAPLAYER 0339 0340 if (d->sharedData->soundtrackPlay) 0341 { 0342 d->playbackWidget->slotPlay(); 0343 } 0344 0345 #endif 0346 0347 } 0348 0349 PresentationWidget::~PresentationWidget() 0350 { 0351 0352 #ifdef HAVE_MEDIAPLAYER 0353 0354 d->playbackWidget->slotStop(); 0355 0356 #endif 0357 0358 d->timer->stop(); 0359 d->mouseMoveTimer->stop(); 0360 0361 if (d->intArray) 0362 { 0363 delete [] d->intArray; 0364 } 0365 0366 delete d->imageLoader; 0367 delete d; 0368 } 0369 0370 void PresentationWidget::readSettings() 0371 { 0372 } 0373 0374 void PresentationWidget::loadNextImage() 0375 { 0376 if (!d->currImage.isNull()) 0377 { 0378 m_firstPainter = false; 0379 m_buffer = d->currImage; 0380 } 0381 else 0382 { 0383 m_buffer = QPixmap(size()); 0384 m_buffer.fill(Qt::black); 0385 } 0386 0387 d->fileIndex++; 0388 0389 d->imageLoader->next(); 0390 int num = d->sharedData->urlList.count(); 0391 0392 if (d->fileIndex >= num) 0393 { 0394 if (d->sharedData->loop) 0395 { 0396 d->fileIndex = 0; 0397 } 0398 else 0399 { 0400 d->currImage = QPixmap(0, 0); 0401 d->fileIndex = num - 1; 0402 return; 0403 } 0404 } 0405 0406 if (!d->sharedData->loop) 0407 { 0408 d->slideCtrlWidget->setEnabledPrev(d->fileIndex > 0); 0409 d->slideCtrlWidget->setEnabledNext(d->fileIndex < num - 1); 0410 } 0411 0412 QImage img = d->imageLoader->getCurrent(); 0413 0414 QPixmap newPixmap = QPixmap::fromImage(img); 0415 QPixmap pixmap(width(), height()); 0416 pixmap.fill(Qt::black); 0417 QPainter p(&pixmap); 0418 0419 p.drawPixmap((width() - newPixmap.width()) / 2, 0420 (height() - newPixmap.height()) / 2, newPixmap, 0421 0, 0, newPixmap.width(), newPixmap.height()); 0422 0423 d->currImage = pixmap; 0424 0425 if (img.isNull()) 0426 { 0427 0428 #ifdef HAVE_MEDIAPLAYER 0429 0430 d->videoView->setCurrentUrl(d->imageLoader->currPath()); 0431 0432 #endif 0433 0434 } 0435 } 0436 0437 void PresentationWidget::loadPrevImage() 0438 { 0439 d->fileIndex--; 0440 d->imageLoader->prev(); 0441 0442 int num = d->sharedData->urlList.count(); 0443 0444 if (d->fileIndex < 0) 0445 { 0446 if (d->sharedData->loop) 0447 { 0448 d->fileIndex = num - 1; 0449 } 0450 else 0451 { 0452 d->fileIndex = -1; // set this to -1. 0453 return; 0454 } 0455 } 0456 0457 if (!d->sharedData->loop) 0458 { 0459 d->slideCtrlWidget->setEnabledPrev(d->fileIndex > 0); 0460 d->slideCtrlWidget->setEnabledNext(d->fileIndex < num - 1); 0461 } 0462 0463 QImage img = d->imageLoader->getCurrent(); 0464 0465 QPixmap newPixmap = QPixmap::fromImage(img); 0466 QPixmap pixmap(width(), height()); 0467 pixmap.fill(Qt::black); 0468 QPainter p(&pixmap); 0469 0470 p.drawPixmap((width() - newPixmap.width()) / 2, 0471 (height() - newPixmap.height()) / 2, newPixmap, 0472 0, 0, newPixmap.width(), newPixmap.height()); 0473 0474 d->currImage = pixmap; 0475 0476 if (img.isNull()) 0477 { 0478 0479 #ifdef HAVE_MEDIAPLAYER 0480 0481 d->videoView->setCurrentUrl(d->imageLoader->currPath()); 0482 0483 #endif 0484 0485 } 0486 } 0487 0488 void PresentationWidget::printFilename() 0489 { 0490 if (d->currImage.isNull()) 0491 { 0492 return; 0493 } 0494 0495 QPainter p; 0496 0497 p.begin(&d->currImage); 0498 p.setPen(Qt::black); 0499 0500 for (int x = 9 ; x <= 11 ; ++x) 0501 { 0502 for (int y = 31 ; y >= 29 ; --y) 0503 { 0504 p.drawText(x, height() - y, d->imageLoader->currFileName()); 0505 } 0506 } 0507 0508 p.setPen(QColor(Qt::white)); 0509 p.drawText(10, height() - 30, d->imageLoader->currFileName()); 0510 } 0511 0512 void PresentationWidget::printComments() 0513 { 0514 if (d->currImage.isNull()) 0515 { 0516 return; 0517 } 0518 0519 DItemInfo info(d->sharedData->iface->itemInfo(d->imageLoader->currPath())); 0520 QString comments = info.comment(); 0521 0522 int yPos = 30; // Text Y coordinate 0523 0524 if (d->sharedData->printFileName) 0525 { 0526 yPos = 50; 0527 } 0528 0529 QStringList commentsByLines; 0530 0531 uint commentsIndex = 0; // Comments QString index 0532 0533 while (commentsIndex < (uint)comments.length()) 0534 { 0535 QString newLine; 0536 bool breakLine = false; // End Of Line found 0537 uint currIndex; // Comments QString current index 0538 0539 // Check minimal lines dimension 0540 0541 uint commentsLinesLengthLocal = d->sharedData->commentsLinesLength; 0542 0543 for (currIndex = commentsIndex ; (currIndex < (uint)comments.length()) && !breakLine ; ++currIndex) 0544 { 0545 if ((comments[currIndex] == QLatin1Char('\n')) || comments[currIndex].isSpace()) 0546 { 0547 breakLine = true; 0548 } 0549 } 0550 0551 if (commentsLinesLengthLocal <= (currIndex - commentsIndex)) 0552 { 0553 commentsLinesLengthLocal = (currIndex - commentsIndex); 0554 } 0555 0556 breakLine = false; 0557 0558 for (currIndex = commentsIndex ; ((currIndex <= (commentsIndex + commentsLinesLengthLocal)) && 0559 (currIndex < (uint)comments.length()) && !breakLine) ; ++currIndex) 0560 { 0561 breakLine = (comments[currIndex] == QLatin1Char('\n')) ? true : false; 0562 0563 if (breakLine) 0564 { 0565 newLine.append(QLatin1Char(' ')); 0566 } 0567 else 0568 { 0569 newLine.append(comments[currIndex]); 0570 } 0571 } 0572 0573 commentsIndex = currIndex; // The line is ended 0574 0575 if (commentsIndex != (uint)comments.length()) 0576 { 0577 while (!newLine.endsWith(QLatin1Char(' '))) 0578 { 0579 newLine.truncate(newLine.length() - 1); 0580 commentsIndex--; 0581 } 0582 } 0583 0584 commentsByLines.prepend(newLine.trimmed()); 0585 } 0586 0587 QPainter p; 0588 0589 p.begin(&d->currImage); 0590 p.setFont(*d->sharedData->captionFont); 0591 0592 for (int lineNumber = 0 ; lineNumber < (int)commentsByLines.count() ; ++lineNumber) 0593 { 0594 p.setPen(QColor(d->sharedData->commentsBgColor)); 0595 0596 // coefficient 1.5 is used to maintain distance between different lines 0597 0598 for (int x = 9 ; x <= 11 ; ++x) 0599 { 0600 for (int y = (int)(yPos + lineNumber * 1.5 * d->sharedData->captionFont->pointSize() + 1) ; 0601 y >= (int)(yPos + lineNumber * 1.5 * d->sharedData->captionFont->pointSize() - 1) ; --y) 0602 { 0603 p.drawText(x, height() - y, commentsByLines[lineNumber]); 0604 } 0605 } 0606 0607 p.setPen(QColor(d->sharedData->commentsFontColor)); 0608 p.drawText(10, height() - (int)(lineNumber * 1.5 * d->sharedData->captionFont->pointSize() + yPos), 0609 commentsByLines[lineNumber]); 0610 } 0611 } 0612 0613 void PresentationWidget::printProgress() 0614 { 0615 if (d->currImage.isNull()) 0616 { 0617 return; 0618 } 0619 0620 QPainter p; 0621 p.begin(&d->currImage); 0622 0623 QString progress(QString::number(d->fileIndex + 1) + QLatin1Char('/') + 0624 QString::number(d->sharedData->urlList.count())); 0625 0626 int stringLength = p.fontMetrics().horizontalAdvance(progress) * progress.length(); 0627 0628 p.setPen(QColor(Qt::black)); 0629 0630 for (int x = 9 ; x <= 11 ; ++x) 0631 { 0632 for (int y = 21 ; y >= 19 ; --y) 0633 { 0634 p.drawText(width() - stringLength - x, y, progress); 0635 } 0636 } 0637 0638 p.setPen(QColor(Qt::white)); 0639 p.drawText(width() - stringLength - 10, 20, progress); 0640 } 0641 0642 void PresentationWidget::showEndOfShow() 0643 { 0644 m_endOfShow = true; 0645 update(); 0646 0647 d->slideCtrlWidget->setEnabledPlay(false); 0648 d->slideCtrlWidget->setEnabledNext(false); 0649 d->slideCtrlWidget->setEnabledPrev(false); 0650 } 0651 0652 void PresentationWidget::showOverlays() 0653 { 0654 if (d->slideCtrlWidget->isHidden()) 0655 { 0656 int w = d->slideCtrlWidget->width() - 1; 0657 d->slideCtrlWidget->move(d->deskWidth - w, 0); 0658 d->slideCtrlWidget->show(); 0659 } 0660 0661 #ifdef HAVE_MEDIAPLAYER 0662 0663 if (d->playbackWidget->isHidden()) 0664 { 0665 d->playbackWidget->move(0, 0); 0666 d->playbackWidget->show(); 0667 } 0668 0669 #endif 0670 0671 } 0672 0673 void PresentationWidget::hideOverlays() 0674 { 0675 d->slideCtrlWidget->hide(); 0676 0677 #ifdef HAVE_MEDIAPLAYER 0678 0679 d->playbackWidget->hide(); 0680 0681 #endif 0682 0683 } 0684 0685 void PresentationWidget::keyPressEvent(QKeyEvent* event) 0686 { 0687 if (!event) 0688 { 0689 return; 0690 } 0691 0692 #ifdef HAVE_MEDIAPLAYER 0693 0694 d->playbackWidget->keyPressEvent(event); 0695 0696 #endif 0697 0698 d->slideCtrlWidget->keyPressEvent(event); 0699 } 0700 0701 void PresentationWidget::mousePressEvent(QMouseEvent* e) 0702 { 0703 if (m_endOfShow) 0704 { 0705 slotClose(); 0706 } 0707 0708 if (e->button() == Qt::LeftButton) 0709 { 0710 d->timer->stop(); 0711 d->slideCtrlWidget->setPaused(!d->sharedData->offAutoDelay); 0712 slotNext(); 0713 } 0714 else if ((e->button() == Qt::RightButton) && ((d->fileIndex - 1) >= 0)) 0715 { 0716 d->timer->stop(); 0717 d->slideCtrlWidget->setPaused(!d->sharedData->offAutoDelay); 0718 slotPrev(); 0719 } 0720 } 0721 0722 void PresentationWidget::mouseMoveEvent(QMouseEvent* e) 0723 { 0724 setCursor(QCursor(Qt::ArrowCursor)); 0725 d->mouseMoveTimer->start(1000); 0726 0727 if (!d->slideCtrlWidget->canHide() 0728 0729 #ifdef HAVE_MEDIAPLAYER 0730 0731 || !d->playbackWidget->canHide() 0732 0733 #endif 0734 0735 ) 0736 { 0737 return; 0738 } 0739 0740 QPoint pos(e->pos()); 0741 0742 if ((pos.y() > 20) && 0743 (pos.y() < (d->deskHeight - 20 - 1))) 0744 { 0745 if (!d->slideCtrlWidget->canHide() 0746 0747 #ifdef HAVE_MEDIAPLAYER 0748 0749 || !d->playbackWidget->canHide() 0750 0751 #endif 0752 0753 ) 0754 { 0755 return; 0756 } 0757 else 0758 { 0759 hideOverlays(); 0760 } 0761 0762 return; 0763 } 0764 0765 showOverlays(); 0766 } 0767 0768 void PresentationWidget::wheelEvent(QWheelEvent* e) 0769 { 0770 if (!d->sharedData->enableMouseWheel) 0771 { 0772 return; 0773 } 0774 0775 if (m_endOfShow) 0776 { 0777 slotClose(); 0778 } 0779 0780 int delta = e->angleDelta().y(); 0781 0782 if (delta < 0) 0783 { 0784 d->timer->stop(); 0785 d->slideCtrlWidget->setPaused(true); 0786 slotNext(); 0787 } 0788 else if ((delta > 0) && ((d->fileIndex - 1) >= 0)) 0789 { 0790 d->timer->stop(); 0791 d->slideCtrlWidget->setPaused(true); 0792 slotPrev(); 0793 } 0794 } 0795 0796 void PresentationWidget::slotMouseMoveTimeOut() 0797 { 0798 QPoint pos(QCursor::pos()); 0799 0800 if ((pos.y() < 20) || 0801 (pos.y() > (d->deskHeight - 20 - 1)) || 0802 !d->timer->isActive() || 0803 d->slideCtrlWidget->underMouse() 0804 0805 #ifdef HAVE_MEDIAPLAYER 0806 0807 || d->playbackWidget->underMouse() 0808 0809 #endif 0810 0811 ) 0812 { 0813 return; 0814 } 0815 0816 setCursor(QCursor(Qt::BlankCursor)); 0817 } 0818 0819 void PresentationWidget::paintEvent(QPaintEvent*) 0820 { 0821 QPainter p(this); 0822 0823 if (m_simplyShow || m_firstPainter) 0824 { 0825 if (d->sharedData->printFileName) 0826 { 0827 printFilename(); 0828 } 0829 0830 if (d->sharedData->printProgress) 0831 { 0832 printProgress(); 0833 } 0834 0835 if (d->sharedData->printFileComments) 0836 { 0837 printComments(); 0838 } 0839 0840 double ratio = devicePixelRatioF(); 0841 QSize fullSize = QSizeF(ratio * width(), ratio * height()).toSize(); 0842 0843 QPixmap pixmap = d->currImage.scaled(fullSize, Qt::KeepAspectRatio, 0844 Qt::SmoothTransformation); 0845 0846 p.drawPixmap(0, 0, width(), height(), pixmap, 0847 0, 0, pixmap.width(), pixmap.height()); 0848 0849 p.end(); 0850 0851 m_simplyShow = false; 0852 0853 return; 0854 } 0855 0856 if (m_endOfShow) 0857 { 0858 p.fillRect(0, 0, width(), height(), Qt::black); 0859 0860 QFont fn(font()); 0861 fn.setPointSize(fn.pointSize() + 10); 0862 fn.setBold(true); 0863 0864 p.setFont(fn); 0865 p.setPen(Qt::white); 0866 p.drawText(100, 100, i18n("Slideshow Completed")); 0867 p.drawText(100, 100 + 10 + fn.pointSize(), i18n("Click to Exit...")); 0868 0869 p.end(); 0870 return; 0871 } 0872 0873 // If execution reach this line, an effect is running 0874 0875 p.drawPixmap(0, 0, m_buffer); 0876 } 0877 0878 void PresentationWidget::startPainter() 0879 { 0880 m_startPainter = true; 0881 repaint(); 0882 } 0883 0884 void PresentationWidget::slotPause() 0885 { 0886 d->timer->stop(); 0887 showOverlays(); 0888 } 0889 0890 void PresentationWidget::slotPlay() 0891 { 0892 hideOverlays(); 0893 slotTimeOut(); 0894 } 0895 0896 void PresentationWidget::slotPrev() 0897 { 0898 loadPrevImage(); 0899 0900 if (d->currImage.isNull() || d->sharedData->urlList.isEmpty()) 0901 { 0902 showEndOfShow(); 0903 return; 0904 } 0905 0906 d->effectRunning = false; 0907 0908 showCurrentImage(); 0909 } 0910 0911 void PresentationWidget::slotNext() 0912 { 0913 loadNextImage(); 0914 0915 if (d->currImage.isNull() || d->sharedData->urlList.isEmpty()) 0916 { 0917 showEndOfShow(); 0918 return; 0919 } 0920 0921 d->effectRunning = false; 0922 0923 showCurrentImage(); 0924 } 0925 0926 void PresentationWidget::slotClose() 0927 { 0928 close(); 0929 } 0930 0931 void PresentationWidget::slotRemoveImageFromList() 0932 { 0933 QUrl url = d->imageLoader->currPath(); 0934 0935 // Delete or move to trash by url 0936 0937 d->sharedData->iface->deleteImage(url); 0938 0939 // Delete from list of presentation 0940 0941 d->sharedData->urlList.removeOne(url); 0942 0943 // Delete from list of mainpage 0944 0945 d->sharedData->mainPage->removeImageFromList(url); 0946 } 0947 0948 void PresentationWidget::slotVideoLoaded(bool loaded) 0949 { 0950 if (loaded) 0951 { 0952 0953 #ifdef HAVE_MEDIAPLAYER 0954 0955 slotPause(); 0956 d->videoView->show(); 0957 0958 #endif 0959 0960 } 0961 } 0962 0963 void PresentationWidget::slotVideoFinished() 0964 { 0965 0966 #ifdef HAVE_MEDIAPLAYER 0967 0968 d->videoView->hide(); 0969 slotPlay(); 0970 0971 #endif 0972 0973 } 0974 0975 // -- Effects rules -------------------------------------------------------------------------------------------------------- 0976 0977 void PresentationWidget::registerEffects() 0978 { 0979 d->Effects.insert(QLatin1String("None"), &PresentationWidget::effectNone); 0980 d->Effects.insert(QLatin1String("Chess Board"), &PresentationWidget::effectChessboard); 0981 d->Effects.insert(QLatin1String("Melt Down"), &PresentationWidget::effectMeltdown); 0982 d->Effects.insert(QLatin1String("Sweep"), &PresentationWidget::effectSweep); 0983 d->Effects.insert(QLatin1String("Mosaic"), &PresentationWidget::effectMosaic); 0984 d->Effects.insert(QLatin1String("Cubism"), &PresentationWidget::effectCubism); 0985 d->Effects.insert(QLatin1String("Growing"), &PresentationWidget::effectGrowing); 0986 d->Effects.insert(QLatin1String("Horizontal Lines"), &PresentationWidget::effectHorizLines); 0987 d->Effects.insert(QLatin1String("Vertical Lines"), &PresentationWidget::effectVertLines); 0988 d->Effects.insert(QLatin1String("Circle Out"), &PresentationWidget::effectCircleOut); 0989 d->Effects.insert(QLatin1String("MultiCircle Out"), &PresentationWidget::effectMultiCircleOut); 0990 d->Effects.insert(QLatin1String("Spiral In"), &PresentationWidget::effectSpiralIn); 0991 d->Effects.insert(QLatin1String("Blobs"), &PresentationWidget::effectBlobs); 0992 } 0993 0994 QStringList PresentationWidget::effectNames() 0995 { 0996 QStringList effects; 0997 0998 effects.append(QLatin1String("None")); 0999 effects.append(QLatin1String("Chess Board")); 1000 effects.append(QLatin1String("Melt Down")); 1001 effects.append(QLatin1String("Sweep")); 1002 effects.append(QLatin1String("Mosaic")); 1003 effects.append(QLatin1String("Cubism")); 1004 effects.append(QLatin1String("Growing")); 1005 effects.append(QLatin1String("Horizontal Lines")); 1006 effects.append(QLatin1String("Vertical Lines")); 1007 effects.append(QLatin1String("Circle Out")); 1008 effects.append(QLatin1String("MultiCircle Out")); 1009 effects.append(QLatin1String("Spiral In")); 1010 effects.append(QLatin1String("Blobs")); 1011 effects.append(QLatin1String("Random")); 1012 1013 return effects; 1014 } 1015 1016 QMap<QString, QString> PresentationWidget::effectNamesI18N() 1017 { 1018 QMap<QString, QString> effects; 1019 1020 effects[QLatin1String("None")] = i18nc("Filter Effect: No effect", "None"); 1021 effects[QLatin1String("Chess Board")] = i18nc("Filter Effect: Chess Board", "Chess Board"); 1022 effects[QLatin1String("Melt Down")] = i18nc("Filter Effect: Melt Down", "Melt Down"); 1023 effects[QLatin1String("Sweep")] = i18nc("Filter Effect: Sweep", "Sweep"); 1024 effects[QLatin1String("Mosaic")] = i18nc("Filter Effect: Mosaic", "Mosaic"); 1025 effects[QLatin1String("Cubism")] = i18nc("Filter Effect: Cubism", "Cubism"); 1026 effects[QLatin1String("Growing")] = i18nc("Filter Effect: Growing", "Growing"); 1027 effects[QLatin1String("Horizontal Lines")] = i18nc("Filter Effect: Horizontal Lines", "Horizontal Lines"); 1028 effects[QLatin1String("Vertical Lines")] = i18nc("Filter Effect: Vertical Lines", "Vertical Lines"); 1029 effects[QLatin1String("Circle Out")] = i18nc("Filter Effect: Circle Out", "Circle Out"); 1030 effects[QLatin1String("MultiCircle Out")] = i18nc("Filter Effect: Multi-Circle Out", "Multi-Circle Out"); 1031 effects[QLatin1String("Spiral In")] = i18nc("Filter Effect: Spiral In", "Spiral In"); 1032 effects[QLatin1String("Blobs")] = i18nc("Filter Effect: Blobs", "Blobs"); 1033 effects[QLatin1String("Random")] = i18nc("Filter Effect: Random effect", "Random"); 1034 1035 return effects; 1036 } 1037 1038 void PresentationWidget::slotTimeOut() 1039 { 1040 if (!d->effect) 1041 { 1042 return; // No effect -> bye ! 1043 } 1044 1045 int tmout = -1; 1046 1047 if (d->effectRunning) // Effect under progress ? 1048 { 1049 tmout = (this->*d->effect)(false); 1050 } 1051 else 1052 { 1053 loadNextImage(); 1054 1055 if (d->sharedData->offAutoDelay) 1056 { 1057 showCurrentImage(); 1058 } 1059 else 1060 { 1061 if (d->currImage.isNull() || d->sharedData->urlList.isEmpty()) // End of slideshow ? 1062 { 1063 showEndOfShow(); 1064 return; 1065 } 1066 1067 if (d->sharedData->effectName == QLatin1String("Random")) // Take a random effect. 1068 { 1069 d->effect = getRandomEffect(); 1070 1071 if (!d->effect) 1072 { 1073 return; 1074 } 1075 } 1076 1077 d->effectRunning = true; 1078 1079 tmout = (this->*d->effect)(true); 1080 } 1081 } 1082 1083 if (tmout <= 0) // Effect finished -> delay. 1084 { 1085 tmout = d->sharedData->delay; 1086 d->effectRunning = false; 1087 } 1088 1089 if (d->sharedData->offAutoDelay) 1090 { 1091 d->timer->stop(); 1092 } 1093 else 1094 { 1095 d->timer->setSingleShot(true); 1096 d->timer->start(tmout); 1097 } 1098 } 1099 1100 void PresentationWidget::showCurrentImage() 1101 { 1102 if (d->currImage.isNull()) 1103 { 1104 return; 1105 } 1106 1107 m_simplyShow = true; 1108 1109 repaint(); 1110 } 1111 1112 PresentationWidget::EffectMethod PresentationWidget::getRandomEffect() 1113 { 1114 QStringList effs = d->Effects.keys(); 1115 effs.removeAt(effs.indexOf(QLatin1String("None"))); 1116 1117 int i = randomGenerator->bounded(effs.count()); 1118 QString key = effs[i]; 1119 d->effectName = key; 1120 1121 return d->Effects[key]; 1122 } 1123 1124 int PresentationWidget::effectNone(bool /* aInit */) 1125 { 1126 showCurrentImage(); 1127 1128 return -1; 1129 } 1130 1131 int PresentationWidget::effectChessboard(bool aInit) 1132 { 1133 if (aInit) 1134 { 1135 d->w = width(); 1136 d->h = height(); 1137 d->dx = 8; // width of one tile 1138 d->dy = 8; // height of one tile 1139 d->j = (d->w + d->dx - 1) / d->dx; // number of tiles 1140 d->x = d->j * d->dx; // shrinking x-offset from screen border 1141 d->ix = 0; // growing x-offset from screen border 1142 d->iy = 0; // 0 or d->dy for growing tiling effect 1143 d->y = (d->j & 1) ? 0 : d->dy; // 0 or d->dy for shrinking tiling effect 1144 d->wait = 800 / d->j; // timeout between effects 1145 } 1146 1147 if (d->ix >= d->w) 1148 { 1149 showCurrentImage(); 1150 return -1; 1151 } 1152 1153 d->ix += d->dx; 1154 d->x -= d->dx; 1155 d->iy = d->iy ? 0 : d->dy; 1156 d->y = d->y ? 0 : d->dy; 1157 1158 QPainter bufferPainter(&m_buffer); 1159 QBrush brush = QBrush(d->currImage); 1160 1161 for (int y = 0 ; y < d->w ; y += (d->dy << 1)) 1162 { 1163 bufferPainter.fillRect(d->ix, y + d->iy, d->dx, d->dy, brush); 1164 bufferPainter.fillRect(d->x, y + d->y, d->dx, d->dy, brush); 1165 } 1166 1167 repaint(); 1168 1169 return d->wait; 1170 } 1171 1172 int PresentationWidget::effectMeltdown(bool aInit) 1173 { 1174 int i; 1175 1176 if (aInit) 1177 { 1178 delete [] d->intArray; 1179 d->w = width(); 1180 d->h = height(); 1181 d->dx = 4; 1182 d->dy = 16; 1183 d->ix = d->w / d->dx; 1184 d->intArray = new int[d->ix]; 1185 1186 for (i = d->ix - 1 ; i >= 0 ; --i) 1187 { 1188 d->intArray[i] = 0; 1189 } 1190 } 1191 1192 d->pdone = true; 1193 1194 int y, x; 1195 QPainter bufferPainter(&m_buffer); 1196 1197 for (i = 0, x = 0 ; i < d->ix ; ++i, x += d->dx) 1198 { 1199 y = d->intArray[i]; 1200 1201 if (y >= d->h) 1202 { 1203 continue; 1204 } 1205 1206 d->pdone = false; 1207 1208 if (randomGenerator->bounded(16U) < 6) 1209 { 1210 continue; 1211 } 1212 /* 1213 bufferPainter.drawPixmap(x, y + d->dy, m_buffer, x, y, d->dx, d->h - y - d->dy); 1214 */ 1215 bufferPainter.drawPixmap(x, y, d->currImage, x, y, d->dx, d->dy); 1216 1217 d->intArray[i] += d->dy; 1218 } 1219 1220 bufferPainter.end(); 1221 1222 repaint(); 1223 1224 if (d->pdone) 1225 { 1226 delete [] d->intArray; 1227 d->intArray = nullptr; 1228 showCurrentImage(); 1229 1230 return -1; 1231 } 1232 1233 return 15; 1234 } 1235 1236 int PresentationWidget::effectSweep(bool aInit) 1237 { 1238 if (aInit) 1239 { 1240 // subtype: 0=sweep right to left, 1=sweep left to right 1241 // 2=sweep bottom to top, 3=sweep top to bottom 1242 1243 d->subType = randomGenerator->bounded(4); 1244 d->w = width(); 1245 d->h = height(); 1246 d->dx = ((d->subType == 1) ? 16 : -16); 1247 d->dy = ((d->subType == 3) ? 16 : -16); 1248 d->x = ((d->subType == 1) ? 0 : d->w); 1249 d->y = ((d->subType == 3) ? 0 : d->h); 1250 } 1251 1252 if ((d->subType == 0) || (d->subType == 1)) 1253 { 1254 // horizontal sweep 1255 1256 if (((d->subType == 0) && (d->x < -64)) || ((d->subType == 1) && (d->x > d->w + 64))) 1257 { 1258 showCurrentImage(); 1259 return -1; 1260 } 1261 1262 int w; 1263 int x; 1264 int i; 1265 1266 for (w = 2, i = 4, x = d->x ; i > 0 ; --i, w <<= 1, x -= d->dx) 1267 { 1268 m_px = x; 1269 m_py = 0; 1270 m_psx = w; 1271 m_psy = d->h; 1272 1273 QPainter bufferPainter(&m_buffer); 1274 bufferPainter.fillRect(m_px, m_py, m_psx, m_psy, QBrush(d->currImage)); 1275 bufferPainter.end(); 1276 1277 repaint(); 1278 } 1279 1280 d->x += d->dx; 1281 } 1282 else 1283 { 1284 // vertical sweep 1285 1286 if (((d->subType == 2) && (d->y < -64)) || ((d->subType == 3) && (d->y > d->h + 64))) 1287 { 1288 showCurrentImage(); 1289 return -1; 1290 } 1291 1292 int h; 1293 int y; 1294 int i; 1295 1296 for (h = 2, i = 4, y = d->y ; i > 0 ; --i, h <<= 1, y -= d->dy) 1297 { 1298 m_px = 0; 1299 m_py = y; 1300 m_psx = d->w; 1301 m_psy = h; 1302 1303 QPainter bufferPainter(&m_buffer); 1304 bufferPainter.fillRect(m_px, m_py, m_psx, m_psy, QBrush(d->currImage)); 1305 bufferPainter.end(); 1306 1307 repaint(); 1308 } 1309 1310 d->y += d->dy; 1311 } 1312 1313 return 20; 1314 } 1315 1316 int PresentationWidget::effectMosaic(bool aInit) 1317 { 1318 int dim = 10; // Size of a cell (dim x dim) 1319 int margin = dim + (int)(dim / 4); 1320 1321 if (aInit) 1322 { 1323 d->i = 30; // giri totaly 1324 d->pixelMatrix = new bool*[width()]; 1325 1326 for (int x = 0 ; x < width() ; ++x) 1327 { 1328 d->pixelMatrix[x] = new bool[height()]; 1329 1330 for (int y = 0 ; y < height() ; ++y) 1331 { 1332 d->pixelMatrix[x][y] = false; 1333 } 1334 } 1335 } 1336 1337 if (d->i <= 0) 1338 { 1339 showCurrentImage(); 1340 return -1; 1341 } 1342 1343 int w = width(); 1344 int h = height(); 1345 1346 QPainter bufferPainter(&m_buffer); 1347 1348 for (int x = 0 ; x < w ; x += randomGenerator->bounded(margin, margin+dim)) 1349 { 1350 for (int y = 0 ; y < h ; y += randomGenerator->bounded(margin, margin+dim)) 1351 { 1352 if (d->pixelMatrix[x][y] == true) 1353 { 1354 if (y != 0) 1355 { 1356 y--; 1357 } 1358 1359 continue; 1360 } 1361 1362 bufferPainter.fillRect(x, y, dim, dim, QBrush(d->currImage)); 1363 1364 for (int i = 0 ; i < dim && (x + i) < w ; ++i) 1365 { 1366 for (int j = 0 ; j < dim && (y + j) < h ; ++j) 1367 { 1368 d->pixelMatrix[x+i][y+j] = true; 1369 } 1370 } 1371 } 1372 } 1373 1374 bufferPainter.end(); 1375 repaint(); 1376 d->i--; 1377 1378 return 20; 1379 } 1380 1381 int PresentationWidget::effectCubism(bool aInit) 1382 { 1383 if (aInit) 1384 { 1385 d->alpha = M_PI * 2; 1386 d->w = width(); 1387 d->h = height(); 1388 d->i = 150; 1389 } 1390 1391 if (d->i <= 0) 1392 { 1393 showCurrentImage(); 1394 return -1; 1395 } 1396 1397 QPainterPath painterPath; 1398 QPainter bufferPainter(&m_buffer); 1399 1400 d->x = randomGenerator->bounded(d->w); 1401 d->y = randomGenerator->bounded(d->h); 1402 int r = randomGenerator->bounded(100, 200); 1403 m_px = d->x - r; 1404 m_py = d->y - r; 1405 m_psx = r; 1406 m_psy = r; 1407 1408 QTransform transform; 1409 transform.rotate(randomGenerator->bounded(-10, 10)); 1410 QRect rect(m_px, m_py, m_psx, m_psy); 1411 bufferPainter.setTransform(transform); 1412 bufferPainter.fillRect(rect, QBrush(d->currImage)); 1413 bufferPainter.end(); 1414 repaint(); 1415 1416 d->i--; 1417 1418 return 10; 1419 } 1420 1421 int PresentationWidget::effectRandom(bool /*aInit*/) 1422 { 1423 d->fileIndex--; 1424 1425 return -1; 1426 } 1427 1428 int PresentationWidget::effectGrowing(bool aInit) 1429 { 1430 if (aInit) 1431 { 1432 d->w = width(); 1433 d->h = height(); 1434 d->x = d->w >> 1; 1435 d->y = d->h >> 1; 1436 d->i = 0; 1437 d->fx = d->x / 100.0; 1438 d->fy = d->y / 100.0; 1439 } 1440 1441 d->x = (d->w >> 1) - (int)(d->i * d->fx); 1442 d->y = (d->h >> 1) - (int)(d->i * d->fy); 1443 d->i++; 1444 1445 if ((d->x < 0) || (d->y < 0)) 1446 { 1447 showCurrentImage(); 1448 1449 return -1; 1450 } 1451 1452 m_px = d->x; 1453 m_py = d->y; 1454 m_psx = d->w - (d->x << 1); 1455 m_psy = d->h - (d->y << 1); 1456 1457 QPainter bufferPainter(&m_buffer); 1458 bufferPainter.fillRect(m_px, m_py, m_psx, m_psy, QBrush(d->currImage)); 1459 bufferPainter.end(); 1460 repaint(); 1461 1462 return 20; 1463 } 1464 1465 int PresentationWidget::effectHorizLines(bool aInit) 1466 { 1467 static const int iyPos[] = { 0, 4, 2, 6, 1, 5, 3, 7, -1 }; 1468 1469 if (aInit) 1470 { 1471 d->w = width(); 1472 d->h = height(); 1473 d->i = 0; 1474 } 1475 1476 if (iyPos[d->i] < 0) 1477 { 1478 return -1; 1479 } 1480 1481 int iPos; 1482 int until = d->h; 1483 1484 QPainter bufferPainter(&m_buffer); 1485 QBrush brush = QBrush(d->currImage); 1486 1487 for (iPos = iyPos[d->i] ; iPos < until ; iPos += 8) 1488 { 1489 bufferPainter.fillRect(0, iPos, d->w, 1, brush); 1490 } 1491 1492 bufferPainter.end(); 1493 repaint(); 1494 1495 d->i++; 1496 1497 if (iyPos[d->i] >= 0) 1498 { 1499 return 160; 1500 } 1501 1502 showCurrentImage(); 1503 1504 return -1; 1505 } 1506 1507 int PresentationWidget::effectVertLines(bool aInit) 1508 { 1509 static const int ixPos[] = { 0, 4, 2, 6, 1, 5, 3, 7, -1 }; 1510 1511 if (aInit) 1512 { 1513 d->w = width(); 1514 d->h = height(); 1515 d->i = 0; 1516 } 1517 1518 if (ixPos[d->i] < 0) 1519 { 1520 return -1; 1521 } 1522 1523 int iPos; 1524 int until = d->w; 1525 1526 QPainter bufferPainter(&m_buffer); 1527 QBrush brush = QBrush(d->currImage); 1528 1529 for (iPos = ixPos[d->i] ; iPos < until ; iPos += 8) 1530 { 1531 bufferPainter.fillRect(iPos, 0, 1, d->h, brush); 1532 } 1533 1534 bufferPainter.end(); 1535 repaint(); 1536 1537 d->i++; 1538 1539 if (ixPos[d->i] >= 0) 1540 { 1541 return 160; 1542 } 1543 1544 showCurrentImage(); 1545 1546 return -1; 1547 } 1548 1549 int PresentationWidget::effectMultiCircleOut(bool aInit) 1550 { 1551 int x, y, i; 1552 double alpha; 1553 1554 if (aInit) 1555 { 1556 startPainter(); 1557 d->w = width(); 1558 d->h = height(); 1559 d->x = d->w; 1560 d->y = d->h >> 1; 1561 d->pa.setPoint(0, d->w >> 1, d->h >> 1); 1562 d->pa.setPoint(3, d->w >> 1, d->h >> 1); 1563 d->fy = sqrt((double)d->w * d->w + d->h * d->h) / 2; 1564 d->i = randomGenerator->bounded(2, 17); 1565 d->fd = M_PI * 2 / d->i; 1566 d->alpha = d->fd; 1567 d->wait = 10 * d->i; 1568 d->fx = M_PI / 32; // divisor must be powers of 8 1569 } 1570 1571 if (d->alpha < 0) 1572 { 1573 showCurrentImage(); 1574 1575 return -1; 1576 } 1577 1578 for (alpha = d->alpha, i = d->i ; i >= 0 ; --i, alpha += d->fd) 1579 { 1580 x = (d->w >> 1) + (int)(d->fy * cos(-alpha)); 1581 y = (d->h >> 1) + (int)(d->fy * sin(-alpha)); 1582 d->x = (d->w >> 1) + (int)(d->fy * cos(-alpha + d->fx)); 1583 d->y = (d->h >> 1) + (int)(d->fy * sin(-alpha + d->fx)); 1584 1585 d->pa.setPoint(1, x, y); 1586 d->pa.setPoint(2, d->x, d->y); 1587 1588 QPainterPath painterPath; 1589 painterPath.addPolygon(QPolygon(d->pa)); 1590 1591 QPainter bufferPainter(&m_buffer); 1592 bufferPainter.fillPath(painterPath, QBrush(d->currImage)); 1593 bufferPainter.end(); 1594 1595 repaint(); 1596 } 1597 1598 d->alpha -= d->fx; 1599 1600 return d->wait; 1601 } 1602 1603 int PresentationWidget::effectSpiralIn(bool aInit) 1604 { 1605 if (aInit) 1606 { 1607 update(); 1608 d->w = width(); 1609 d->h = height(); 1610 d->ix = d->w / 8; 1611 d->iy = d->h / 8; 1612 d->x0 = 0; 1613 d->x1 = d->w - d->ix; 1614 d->y0 = d->iy; 1615 d->y1 = d->h - d->iy; 1616 d->dx = d->ix; 1617 d->dy = 0; 1618 d->i = 0; 1619 d->j = 16 * 16; 1620 d->x = 0; 1621 d->y = 0; 1622 } 1623 1624 if ((d->i == 0) && (d->x0 >= d->x1)) 1625 { 1626 showCurrentImage(); 1627 1628 return -1; 1629 } 1630 1631 if ((d->i == 0) && (d->x >= d->x1)) // switch to: down on right side 1632 { 1633 d->i = 1; 1634 d->dx = 0; 1635 d->dy = d->iy; 1636 d->x1 -= d->ix; 1637 } 1638 else if ((d->i == 1) && (d->y >= d->y1)) // switch to: right to left on bottom side 1639 { 1640 d->i = 2; 1641 d->dx = -d->ix; 1642 d->dy = 0; 1643 d->y1 -= d->iy; 1644 } 1645 else if ((d->i == 2) && (d->x <= d->x0)) // switch to: up on left side 1646 { 1647 d->i = 3; 1648 d->dx = 0; 1649 d->dy = -d->iy; 1650 d->x0 += d->ix; 1651 } 1652 else if ((d->i == 3) && (d->y <= d->y0)) // switch to: left to right on top side 1653 { 1654 d->i = 0; 1655 d->dx = d->ix; 1656 d->dy = 0; 1657 d->y0 += d->iy; 1658 } 1659 1660 m_px = d->x; 1661 m_py = d->y; 1662 m_psx = d->ix; 1663 m_psy = d->iy; 1664 1665 QPainter bufferPainter(&m_buffer); 1666 bufferPainter.fillRect(m_px, m_py, m_psx, m_psy, QBrush(d->currImage)); 1667 bufferPainter.end(); 1668 repaint(); 1669 1670 d->x += d->dx; 1671 d->y += d->dy; 1672 d->j--; 1673 1674 return 8; 1675 } 1676 1677 int PresentationWidget::effectCircleOut(bool aInit) 1678 { 1679 int x, y; 1680 1681 if (aInit) 1682 { 1683 startPainter(); 1684 d->w = width(); 1685 d->h = height(); 1686 d->x = d->w; 1687 d->y = d->h >> 1; 1688 d->alpha = 2 * M_PI; 1689 d->pa.setPoint(0, d->w >> 1, d->h >> 1); 1690 d->pa.setPoint(3, d->w >> 1, d->h >> 1); 1691 d->fx = M_PI / 16; // divisor must be powers of 8 1692 d->fy = sqrt((double)d->w * d->w + d->h * d->h) / 2; 1693 } 1694 1695 if (d->alpha < 0) 1696 { 1697 showCurrentImage(); 1698 1699 return -1; 1700 } 1701 1702 x = d->x; 1703 y = d->y; 1704 d->x = (d->w >> 1) + (int)(d->fy * cos(d->alpha)); 1705 d->y = (d->h >> 1) + (int)(d->fy * sin(d->alpha)); 1706 d->alpha -= d->fx; 1707 1708 d->pa.setPoint(1, x, y); 1709 d->pa.setPoint(2, d->x, d->y); 1710 1711 QPainterPath painterPath; 1712 painterPath.addPolygon(QPolygon(d->pa)); 1713 QPainter bufferPainter(&m_buffer); 1714 bufferPainter.fillPath(painterPath, QBrush(d->currImage)); 1715 bufferPainter.end(); 1716 repaint(); 1717 1718 return 20; 1719 } 1720 1721 int PresentationWidget::effectBlobs(bool aInit) 1722 { 1723 int r; 1724 1725 if (aInit) 1726 { 1727 d->alpha = M_PI * 2; 1728 d->w = width(); 1729 d->h = height(); 1730 d->i = 150; 1731 } 1732 1733 if (d->i <= 0) 1734 { 1735 showCurrentImage(); 1736 1737 return -1; 1738 } 1739 1740 d->x = randomGenerator->bounded(d->w); 1741 d->y = randomGenerator->bounded(d->h); 1742 r = randomGenerator->bounded(50, 250); 1743 m_px = d->x - r; 1744 m_py = d->y - r; 1745 m_psx = r; 1746 m_psy = r; 1747 1748 QPainterPath painterPath; 1749 painterPath.addEllipse(m_px, m_py, m_psx, m_psy); 1750 QPainter bufferPainter(&m_buffer); 1751 bufferPainter.fillPath(painterPath, QBrush(d->currImage)); 1752 bufferPainter.end(); 1753 repaint(); 1754 1755 d->i--; 1756 1757 return 10; 1758 } 1759 1760 } // namespace DigikamGenericPresentationPlugin 1761 1762 #include "moc_presentationwidget.cpp"