File indexing completed on 2025-03-09 03:58:43

0001 /* ============================================================
0002  *
0003  * This file is a part of digiKam project
0004  * https://www.digikam.org
0005  *
0006  * Date        : 2012-26-07
0007  * Description : Main view for import tool
0008  *
0009  * SPDX-FileCopyrightText: 2012      by Islam Wazery <wazery at ubuntu dot com>
0010  * SPDX-FileCopyrightText: 2012-2024 by Gilles Caulier <caulier dot gilles at gmail dot com>
0011  *
0012  * SPDX-License-Identifier: GPL-2.0-or-later
0013  *
0014  * ============================================================ */
0015 
0016 #include "importview.h"
0017 
0018 // Qt includes
0019 
0020 #include <QApplication>
0021 #include <QTimer>
0022 #include <QShortcut>
0023 
0024 // KDE includes
0025 
0026 #include <ksharedconfig.h>
0027 #include <kconfiggroup.h>
0028 
0029 // Local includes
0030 
0031 #include "digikam_debug.h"
0032 #include "digikam_config.h"
0033 #include "digikam_globals.h"
0034 #include "dmessagebox.h"
0035 #include "importiconview.h"
0036 #include "thumbnailsize.h"
0037 #include "fileactionmngr.h"
0038 #include "importsettings.h"
0039 #include "sidebar.h"
0040 #include "dzoombar.h"
0041 #include "camitemsortsettings.h"
0042 
0043 #ifdef HAVE_GEOLOCATION
0044 #   include "mapwidgetview.h"
0045 #endif // HAVE_GEOLOCATION
0046 
0047 namespace Digikam
0048 {
0049 
0050 class Q_DECL_HIDDEN ImportView::Private
0051 {
0052 public:
0053 
0054     explicit Private()
0055       : thumbSize     (ThumbnailSize::Medium),
0056         dockArea      (nullptr),
0057         splitter      (nullptr),
0058         selectionTimer(nullptr),
0059         thumbSizeTimer(nullptr),
0060         parent        (nullptr),
0061         iconView      (nullptr),
0062 
0063 #ifdef HAVE_GEOLOCATION
0064 
0065         mapView(nullptr),
0066 
0067 #endif // HAVE_GEOLOCATION
0068 
0069         stackedView(nullptr),
0070         lastViewMode(ImportStackedView::PreviewCameraMode)
0071 /*
0072         FIXME
0073         , filterWidget(0)
0074 */
0075     {
0076     }
0077 
0078     void addPageUpDownActions(ImportView* const q, QWidget* const w);
0079 
0080 public:
0081 
0082     int                                thumbSize;
0083 
0084     QMainWindow*                       dockArea;
0085 
0086     SidebarSplitter*                   splitter;
0087 
0088     QTimer*                            selectionTimer;
0089     QTimer*                            thumbSizeTimer;
0090 
0091     ImportUI*                          parent;
0092 
0093     ImportIconView*                    iconView;
0094 
0095 #ifdef HAVE_GEOLOCATION
0096 
0097     MapWidgetView*                     mapView;
0098 
0099 #endif // HAVE_GEOLOCATION
0100 
0101     ImportStackedView*                 stackedView;
0102     ImportStackedView::StackedViewMode lastViewMode;
0103 /*
0104     FIXME
0105     FilterSideBarWidget*               filterWidget;
0106 */
0107 };
0108 
0109 void ImportView::Private::addPageUpDownActions(ImportView* const q, QWidget* const w)
0110 {
0111     defineShortcut(w, Qt::Key_PageDown, q, SLOT(slotNextItem()));
0112     defineShortcut(w, Qt::Key_Down,     q, SLOT(slotNextItem()));
0113     defineShortcut(w, Qt::Key_Right,    q, SLOT(slotNextItem()));
0114 
0115     defineShortcut(w, Qt::Key_PageUp,   q, SLOT(slotPrevItem()));
0116     defineShortcut(w, Qt::Key_Up,       q, SLOT(slotPrevItem()));
0117     defineShortcut(w, Qt::Key_Left,     q, SLOT(slotPrevItem()));
0118 }
0119 
0120 ImportView::ImportView(ImportUI* const ui, QWidget* const parent)
0121     : DHBox(parent),
0122       d(new Private)
0123 {
0124     d->parent   = static_cast<ImportUI*>(ui);
0125     d->splitter = new SidebarSplitter;
0126     d->splitter->setFrameStyle(QFrame::NoFrame);
0127     d->splitter->setFrameShadow(QFrame::Plain);
0128     d->splitter->setFrameShape(QFrame::NoFrame);
0129     d->splitter->setOpaqueResize(false);
0130     d->splitter->setParent(this);
0131 
0132     // The dock area where the thumbnail bar is allowed to go.
0133     // TODO qmainwindow here?
0134 
0135     d->dockArea    = new QMainWindow(this, Qt::Widget);
0136     d->splitter->addWidget(d->dockArea);
0137     d->stackedView = new ImportStackedView(d->dockArea);
0138     d->stackedView->setViewMode(ImportStackedView::PreviewCameraMode); // call here, because the models need to be set first..
0139     d->dockArea->setCentralWidget(d->stackedView);
0140     d->stackedView->setDockArea(d->dockArea);
0141 
0142     d->iconView = d->stackedView->importIconView();
0143 
0144 #ifdef HAVE_GEOLOCATION
0145 
0146     d->mapView  = d->stackedView->mapWidgetView();
0147 
0148 #endif // HAVE_GEOLOCATION
0149 
0150     d->addPageUpDownActions(this, d->stackedView->importPreviewView());
0151     d->addPageUpDownActions(this, d->stackedView->thumbBar());
0152 
0153 #ifdef HAVE_MEDIAPLAYER
0154 
0155     d->addPageUpDownActions(this, d->stackedView->mediaPlayerView());
0156 
0157 #endif //HAVE_MEDIAPLAYER
0158 
0159     d->selectionTimer = new QTimer(this);
0160     d->selectionTimer->setSingleShot(true);
0161     d->selectionTimer->setInterval(75);
0162 
0163     d->thumbSizeTimer = new QTimer(this);
0164     d->thumbSizeTimer->setSingleShot(true);
0165     d->thumbSizeTimer->setInterval(300);
0166 
0167     setupConnections();
0168 
0169     loadViewState();
0170 }
0171 
0172 ImportView::~ImportView()
0173 {
0174     saveViewState();
0175     delete d;
0176 }
0177 
0178 void ImportView::applySettings()
0179 {
0180 /*
0181     refreshView();
0182 */
0183 }
0184 
0185 void ImportView::refreshView()
0186 {
0187 /*
0188     d->rightSideBar->refreshTagsView();
0189 */
0190 }
0191 
0192 void ImportView::setupConnections()
0193 {
0194     // -- ImportUI connections ----------------------------------
0195 
0196     connect(d->parent, SIGNAL(signalEscapePressed()),
0197             this, SLOT(slotEscapePreview()));
0198 
0199     // Preview items while download.
0200 
0201     connect(d->parent, SIGNAL(signalPreviewRequested(CamItemInfo,bool)),
0202             this, SLOT(slotTogglePreviewMode(CamItemInfo,bool)));
0203 
0204     // -- IconView Connections -------------------------------------
0205 
0206     connect(d->iconView->model(), SIGNAL(rowsInserted(QModelIndex,int,int)),
0207             this, SLOT(slotImageSelected()));
0208 
0209     connect(d->iconView->model(), SIGNAL(rowsRemoved(QModelIndex,int,int)),
0210             this, SLOT(slotImageSelected()));
0211 
0212     connect(d->iconView->model(), SIGNAL(layoutChanged()),
0213             this, SLOT(slotImageSelected()));
0214 
0215     connect(d->iconView, SIGNAL(selectionChanged()),
0216             this, SLOT(slotImageSelected()));
0217 
0218     connect(d->iconView, SIGNAL(previewRequested(CamItemInfo,bool)),
0219             this, SLOT(slotTogglePreviewMode(CamItemInfo,bool)));
0220 
0221     connect(d->iconView, SIGNAL(zoomOutStep()),
0222             this, SLOT(slotZoomOut()));
0223 
0224     connect(d->iconView, SIGNAL(zoomInStep()),
0225             this, SLOT(slotZoomIn()));
0226 
0227     // -- Preview image widget Connections ------------------------
0228 
0229     connect(d->stackedView, SIGNAL(signalNextItem()),
0230             this, SLOT(slotNextItem()));
0231 
0232     connect(d->stackedView, SIGNAL(signalPrevItem()),
0233             this, SLOT(slotPrevItem()));
0234 
0235     connect(d->stackedView, SIGNAL(signalViewModeChanged()),
0236             this, SLOT(slotViewModeChanged()));
0237 
0238     connect(d->stackedView, SIGNAL(signalEscapePreview()),
0239             this, SLOT(slotEscapePreview()));
0240 
0241     connect(d->stackedView, SIGNAL(signalZoomFactorChanged(double)),
0242             this, SLOT(slotZoomFactorChanged(double)));
0243 
0244     // -- FileActionMngr progress ---------------
0245 
0246     connect(FileActionMngr::instance(), SIGNAL(signalImageChangeFailed(QString,QStringList)),
0247             this, SLOT(slotImageChangeFailed(QString,QStringList)));
0248 
0249     // -- timers ---------------
0250 
0251     connect(d->selectionTimer, SIGNAL(timeout()),
0252             this, SLOT(slotDispatchImageSelected()));
0253 
0254     connect(d->thumbSizeTimer, SIGNAL(timeout()),
0255             this, SLOT(slotThumbSizeEffect()) );
0256 
0257     // -- Import Settings ----------------
0258 /*
0259     connect(ImportSettings::instance(), SIGNAL(setupChanged()),
0260             this, SLOT(slotSidebarTabTitleStyleChanged()));
0261 */
0262 }
0263 
0264 /*
0265 void ImportView::connectIconViewFilter(FilterStatusBar* filterbar)
0266 {
0267     ItemAlbumFilterModel* const model = d->iconView->imageAlbumFilterModel();
0268 
0269     connect(model, SIGNAL(filterMatches(bool)),
0270             filterbar, SLOT(slotFilterMatches(bool)));
0271 
0272     connect(model, SIGNAL(filterSettingsChanged(ItemFilterSettings)),
0273             filterbar, SLOT(slotFilterSettingsChanged(ItemFilterSettings)));
0274 
0275     connect(filterbar, SIGNAL(signalResetFilters()),
0276             d->filterWidget, SLOT(slotResetFilters()));
0277 
0278     connect(filterbar, SIGNAL(signalPopupFiltersView()),
0279             this, SLOT(slotPopupFiltersView()));
0280 }
0281 
0282 void ImportView::slotPopupFiltersView()
0283 {
0284     d->rightSideBar->setActiveTab(d->filterWidget);
0285     d->filterWidget->setFocusToTextFilter();
0286 }
0287 */
0288 
0289 void ImportView::loadViewState()
0290 {
0291 /*
0292     TODO
0293     d->filterWidget->loadState();
0294 */
0295     KSharedConfig::Ptr config = KSharedConfig::openConfig();
0296     KConfigGroup group        = config->group(QLatin1String("Import MainWindow"));
0297 
0298     // Restore the splitter
0299 
0300     d->splitter->restoreState(group);
0301 
0302     // Restore the thumbnail bar dock.
0303 
0304     QByteArray thumbbarState;
0305     thumbbarState = group.readEntry("ThumbbarState", thumbbarState);
0306     d->dockArea->restoreState(QByteArray::fromBase64(thumbbarState));
0307 
0308 #ifdef HAVE_GEOLOCATION
0309 
0310     d->mapView->loadState();
0311 
0312 #endif // HAVE_GEOLOCATION
0313 
0314 }
0315 
0316 void ImportView::saveViewState()
0317 {
0318     KSharedConfig::Ptr config = KSharedConfig::openConfig();
0319     KConfigGroup group        = config->group(QLatin1String("Import MainWindow"));
0320 /*
0321     TODO
0322     d->filterWidget->saveState();
0323 */
0324 
0325     // Save the splitter states.
0326 
0327     d->splitter->saveState(group);
0328 
0329     // Save the position and size of the thumbnail bar. The thumbnail bar dock
0330     // needs to be closed explicitly, because when it is floating and visible
0331     // (when the user is in image preview mode) when the layout is saved, it
0332     // also reappears when restoring the view, while it should always be hidden.
0333 
0334     d->stackedView->thumbBarDock()->close();
0335     group.writeEntry("ThumbbarState", d->dockArea->saveState().toBase64());
0336 
0337 #ifdef HAVE_GEOLOCATION
0338 
0339     d->mapView->saveState();
0340 
0341 #endif // HAVE_GEOLOCATION
0342 
0343 }
0344 
0345 CamItemInfo ImportView::camItemInfo(const QString& folder, const QString& file) const
0346 {
0347     return d->iconView->camItemInfo(folder, file);
0348 }
0349 
0350 CamItemInfo& ImportView::camItemInfoRef(const QString& folder, const QString& file) const
0351 {
0352     return d->iconView->camItemInfoRef(folder, file);
0353 }
0354 
0355 bool ImportView::hasImage(const CamItemInfo& info) const
0356 {
0357     return d->iconView->importItemModel()->hasImage(info);
0358 }
0359 
0360 QList<QUrl> ImportView::allUrls() const
0361 {
0362     return d->iconView->urls();
0363 }
0364 
0365 QList<QUrl> ImportView::selectedUrls() const
0366 {
0367     return d->iconView->selectedUrls();
0368 }
0369 
0370 QList<CamItemInfo> ImportView::selectedCamItemInfos() const
0371 {
0372     return d->iconView->selectedCamItemInfos();
0373 }
0374 
0375 QList<CamItemInfo> ImportView::allItems() const
0376 {
0377     return d->iconView->camItemInfos();
0378 }
0379 
0380 void ImportView::setSelectedCamItemInfos(const CamItemInfoList& infos) const
0381 {
0382     d->iconView->setSelectedCamItemInfos(infos);
0383 }
0384 
0385 int ImportView::downloadedCamItemInfos() const
0386 {
0387     QList<CamItemInfo> infos = d->iconView->camItemInfos();
0388     int numberOfDownloaded   = 0;
0389 
0390     Q_FOREACH (const CamItemInfo& info, infos)
0391     {
0392         if (info.downloaded == CamItemInfo::DownloadedYes)
0393         {
0394             ++numberOfDownloaded; // cppcheck-suppress useStlAlgorithm
0395         }
0396     }
0397 
0398     return numberOfDownloaded;
0399 }
0400 
0401 bool ImportView::isSelected(const QUrl& url) const
0402 {
0403     QList<QUrl> urlsList = selectedUrls();
0404 
0405     Q_FOREACH (const QUrl& selected, urlsList)
0406     {
0407         if (url == selected)
0408         {   // cppcheck-suppress useStlAlgorithm
0409             return true;
0410         }
0411     }
0412 
0413     return false;
0414 }
0415 
0416 void ImportView::slotFirstItem()
0417 {
0418     d->iconView->toFirstIndex();
0419 }
0420 
0421 void ImportView::slotPrevItem()
0422 {
0423     d->iconView->toPreviousIndex();
0424 }
0425 
0426 void ImportView::slotNextItem()
0427 {
0428     d->iconView->toNextIndex();
0429 }
0430 
0431 void ImportView::slotLastItem()
0432 {
0433     d->iconView->toLastIndex();
0434 }
0435 
0436 void ImportView::slotSelectItemByUrl(const QUrl& url)
0437 {
0438     d->iconView->toIndex(url);
0439 }
0440 
0441 void ImportView::slotImageSelected()
0442 {
0443     // delay to slotDispatchImageSelected
0444 
0445     d->selectionTimer->start();
0446     Q_EMIT signalSelectionChanged(d->iconView->numberOfSelectedIndexes());
0447 }
0448 
0449 void ImportView::slotDispatchImageSelected()
0450 {
0451     // the list of CamItemInfos of currently selected items, currentItem first
0452     // since the iconView tracks the changes also while we are in map widget mode,
0453     // we can still pull the data from the iconView
0454 
0455     const CamItemInfoList& list      = d->iconView->selectedCamItemInfosCurrentFirst();
0456     const CamItemInfoList& allImages = d->iconView->camItemInfos();
0457 
0458     if (list.isEmpty())
0459     {
0460         d->stackedView->setPreviewItem();
0461         Q_EMIT signalImageSelected(list, allImages);
0462         Q_EMIT signalNewSelection(false);
0463         Q_EMIT signalNoCurrentItem();
0464     }
0465     else
0466     {
0467         CamItemInfo previousInfo;
0468         CamItemInfo nextInfo;
0469 
0470         if (viewMode() != ImportStackedView::MapWidgetMode)
0471         {
0472             previousInfo = d->iconView->previousInfo(list.first());
0473             nextInfo     = d->iconView->nextInfo(list.first());
0474         }
0475 
0476         if ((viewMode() != ImportStackedView::PreviewCameraMode) &&
0477             (viewMode() != ImportStackedView::MapWidgetMode))
0478         {
0479             d->stackedView->setPreviewItem(list.first(), previousInfo, nextInfo);
0480         }
0481 
0482         Q_EMIT signalImageSelected(list, allImages);
0483         Q_EMIT signalNewSelection(true);
0484     }
0485 }
0486 
0487 double ImportView::zoomMin() const
0488 {
0489     return d->stackedView->zoomMin();
0490 }
0491 
0492 double ImportView::zoomMax() const
0493 {
0494     return d->stackedView->zoomMax();
0495 }
0496 
0497 void ImportView::setZoomFactor(double zoom)
0498 {
0499     d->stackedView->setZoomFactorSnapped(zoom);
0500 }
0501 
0502 void ImportView::slotZoomFactorChanged(double zoom)
0503 {
0504     toggleZoomActions();
0505     Q_EMIT signalZoomChanged(zoom);
0506 }
0507 
0508 void ImportView::setThumbSize(int size)
0509 {
0510     if      (viewMode() == ImportStackedView::PreviewImageMode)
0511     {
0512         double z = DZoomBar::zoomFromSize(size, zoomMin(), zoomMax());
0513         setZoomFactor(z);
0514     }
0515     else if (viewMode() == ImportStackedView::PreviewCameraMode)
0516     {
0517         if      (size > ThumbnailSize::maxThumbsSize())
0518         {
0519             d->thumbSize = ThumbnailSize::maxThumbsSize();
0520         }
0521         else if (size < ThumbnailSize::Small)
0522         {
0523             d->thumbSize = ThumbnailSize::Small;
0524         }
0525         else
0526         {
0527             d->thumbSize = size;
0528         }
0529 
0530         Q_EMIT signalThumbSizeChanged(d->thumbSize);
0531 
0532         d->thumbSizeTimer->start();
0533     }
0534 }
0535 
0536 ThumbnailSize ImportView::thumbnailSize() const
0537 {
0538     return ThumbnailSize(d->thumbSize);
0539 }
0540 
0541 void ImportView::slotThumbSizeEffect()
0542 {
0543     d->iconView->setThumbnailSize(ThumbnailSize(d->thumbSize));
0544     toggleZoomActions();
0545 
0546     ImportSettings::instance()->setDefaultIconSize(d->thumbSize);
0547 }
0548 
0549 void ImportView::toggleZoomActions()
0550 {
0551     if      (viewMode() == ImportStackedView::PreviewImageMode)
0552     {
0553         d->parent->enableZoomMinusAction(true);
0554         d->parent->enableZoomPlusAction(true);
0555 
0556         if (d->stackedView->maxZoom())
0557         {
0558             d->parent->enableZoomPlusAction(false);
0559         }
0560 
0561         if (d->stackedView->minZoom())
0562         {
0563             d->parent->enableZoomMinusAction(false);
0564         }
0565     }
0566     else if (viewMode() == ImportStackedView::PreviewCameraMode)
0567     {
0568         d->parent->enableZoomMinusAction(true);
0569         d->parent->enableZoomPlusAction(true);
0570 
0571         if (d->thumbSize >= ThumbnailSize::maxThumbsSize())
0572         {
0573             d->parent->enableZoomPlusAction(false);
0574         }
0575 
0576         if (d->thumbSize <= ThumbnailSize::Small)
0577         {
0578             d->parent->enableZoomMinusAction(false);
0579         }
0580     }
0581     else
0582     {
0583         d->parent->enableZoomMinusAction(false);
0584         d->parent->enableZoomPlusAction(false);
0585     }
0586 }
0587 
0588 void ImportView::slotZoomIn()
0589 {
0590     if      (viewMode() == ImportStackedView::PreviewCameraMode)
0591     {
0592         setThumbSize(d->thumbSize + ThumbnailSize::Step);
0593         toggleZoomActions();
0594         Q_EMIT signalThumbSizeChanged(d->thumbSize);
0595     }
0596     else if (viewMode() == ImportStackedView::PreviewImageMode)
0597     {
0598         d->stackedView->increaseZoom();
0599     }
0600 }
0601 
0602 void ImportView::slotZoomOut()
0603 {
0604     if      (viewMode() == ImportStackedView::PreviewCameraMode)
0605     {
0606         setThumbSize(d->thumbSize - ThumbnailSize::Step);
0607         toggleZoomActions();
0608         Q_EMIT signalThumbSizeChanged(d->thumbSize);
0609     }
0610     else if (viewMode() == ImportStackedView::PreviewImageMode)
0611     {
0612         d->stackedView->decreaseZoom();
0613     }
0614 }
0615 
0616 void ImportView::slotZoomTo100Percents()
0617 {
0618     if (viewMode() == ImportStackedView::PreviewImageMode)
0619     {
0620         d->stackedView->toggleFitToWindowOr100();
0621     }
0622 }
0623 
0624 void ImportView::slotFitToWindow()
0625 {
0626     if      (viewMode() == ImportStackedView::PreviewCameraMode)
0627     {
0628         int nts = d->iconView->fitToWidthIcons();
0629         setThumbSize(nts);
0630         toggleZoomActions();
0631         Q_EMIT signalThumbSizeChanged(d->thumbSize);
0632     }
0633     else if (viewMode() == ImportStackedView::PreviewImageMode)
0634     {
0635         d->stackedView->fitToWindow();
0636     }
0637 }
0638 
0639 void ImportView::slotEscapePreview()
0640 {
0641     if (viewMode() == ImportStackedView::PreviewCameraMode)
0642 /*
0643         TODO
0644         || viewMode() == ImportStackedView::WelcomePageMode)
0645 */
0646     {
0647         return;
0648     }
0649 
0650     // pass a null camera item info, because we want to fall back to the old
0651     // view mode
0652 
0653     slotTogglePreviewMode(CamItemInfo(), false);
0654 }
0655 
0656 void ImportView::slotMapWidgetView()
0657 {
0658     d->stackedView->setViewMode(ImportStackedView::MapWidgetMode);
0659 }
0660 
0661 void ImportView::slotIconView()
0662 {
0663     if (viewMode() == ImportStackedView::PreviewImageMode)
0664     {
0665         Q_EMIT signalThumbSizeChanged(d->iconView->thumbnailSize().size());
0666     }
0667 
0668     // and switch to icon view
0669 
0670     d->stackedView->setViewMode(ImportStackedView::PreviewCameraMode);
0671 
0672     // make sure the next/previous buttons are updated
0673 
0674     slotImageSelected();
0675 }
0676 
0677 void ImportView::slotImagePreview()
0678 {
0679     const int   currentPreviewMode = viewMode();
0680     CamItemInfo currentInfo;
0681 
0682     if      (currentPreviewMode == ImportStackedView::PreviewCameraMode)
0683     {
0684         currentInfo = d->iconView->currentInfo();
0685     }
0686 
0687 #ifdef HAVE_GEOLOCATION
0688 
0689     // TODO: Implement MapWidget
0690     else if (currentPreviewMode == ImportStackedView::MapWidgetMode)
0691     {
0692         currentInfo = d->mapView->currentCamItemInfo();
0693     }
0694 
0695 #endif // HAVE_GEOLOCATION
0696 
0697     slotTogglePreviewMode(currentInfo, false);
0698 }
0699 
0700 /**
0701  * @brief This method toggles between IconView/MapWidgetView and ImportPreview modes, depending on the context.
0702  */
0703 void ImportView::slotTogglePreviewMode(const CamItemInfo& info, bool downloadPreview)
0704 {
0705     if (!d->parent->cameraUseUMSDriver())
0706     {
0707         return;
0708     }
0709 
0710     if (((viewMode() == ImportStackedView::PreviewCameraMode) ||
0711          (viewMode() == ImportStackedView::MapWidgetMode) || downloadPreview) &&
0712          !info.isNull())
0713     {
0714         d->lastViewMode      = viewMode();
0715         CamItemInfo previous = CamItemInfo();
0716 
0717         if (!downloadPreview)
0718         {
0719             previous = d->iconView->previousInfo(info);
0720         }
0721 
0722         d->stackedView->setPreviewItem(info, previous, d->iconView->nextInfo(info));
0723     }
0724     else
0725     {
0726         // go back to either CameraViewMode or MapWidgetMode
0727 
0728         d->stackedView->setViewMode(d->lastViewMode);
0729     }
0730 
0731     if (!downloadPreview)
0732     {
0733         // make sure the next/previous buttons are updated
0734 
0735         slotImageSelected();
0736     }
0737 }
0738 
0739 void ImportView::slotViewModeChanged()
0740 {
0741     toggleZoomActions();
0742 
0743     switch (viewMode())
0744     {
0745         case ImportStackedView::PreviewCameraMode:
0746             Q_EMIT signalSwitchedToIconView();
0747             Q_EMIT signalThumbSizeChanged(d->iconView->thumbnailSize().size());
0748             break;
0749 
0750         case ImportStackedView::PreviewImageMode:
0751             Q_EMIT signalSwitchedToPreview();
0752             slotZoomFactorChanged(d->stackedView->zoomFactor());
0753             break;
0754 /* TODO
0755         case ImportStackedView::WelcomePageMode:
0756             Q_EMIT signalSwitchedToIconView();
0757             break;
0758 */
0759 
0760         case ImportStackedView::MediaPlayerMode:
0761             Q_EMIT signalSwitchedToPreview();
0762             break;
0763 
0764         case ImportStackedView::MapWidgetMode:
0765             Q_EMIT signalSwitchedToMapView();
0766 
0767             // TODO: connect map view's zoom buttons to main status bar zoom buttons
0768 
0769             break;
0770     }
0771 }
0772 
0773 // TODO: Delete or implement this.
0774 void ImportView::slotImageRename()
0775 {
0776     d->iconView->rename();
0777 }
0778 
0779 void ImportView::slotSelectAll()
0780 {
0781     d->iconView->selectAll();
0782 }
0783 
0784 void ImportView::slotSelectNone()
0785 {
0786     d->iconView->clearSelection();
0787 }
0788 
0789 void ImportView::slotSelectInvert()
0790 {
0791     d->iconView->invertSelection();
0792 }
0793 
0794 void ImportView::slotSortImagesBy(int sortBy)
0795 {
0796     ImportSettings* const settings = ImportSettings::instance();
0797 
0798     if (!settings)
0799     {
0800         return;
0801     }
0802 
0803     settings->setImageSortBy(sortBy);
0804     d->iconView->importFilterModel()->setSortRole((CamItemSortSettings::SortRole) sortBy);
0805 }
0806 
0807 void ImportView::slotSortImagesOrder(int order)
0808 {
0809     ImportSettings* const settings = ImportSettings::instance();
0810 
0811     if (!settings)
0812     {
0813         return;
0814     }
0815 
0816     settings->setImageSortOrder(order);
0817     d->iconView->importFilterModel()->setSortOrder((CamItemSortSettings::SortOrder) order);
0818 }
0819 
0820 void ImportView::slotSeparateImages(int categoryMode)
0821 {
0822     ImportSettings* const settings = ImportSettings::instance();
0823 
0824     if (!settings)
0825     {
0826         return;
0827     }
0828 
0829     settings->setImageSeparationMode(categoryMode);
0830     d->iconView->importFilterModel()->setCategorizationMode((CamItemSortSettings::CategorizationMode) categoryMode);
0831 }
0832 
0833 void ImportView::toggleShowBar(bool b)
0834 {
0835     d->stackedView->thumbBarDock()->showThumbBar(b);
0836 
0837     // See bug #319876 : force to reload current view mode to set thumbbar visibility properly.
0838 
0839     d->stackedView->setViewMode(viewMode());
0840 }
0841 
0842 void ImportView::scrollTo(const QString& folder, const QString& file)
0843 {
0844     CamItemInfo info  = camItemInfo(folder, file);
0845     QModelIndex index = d->iconView->importFilterModel()->indexForCamItemInfo(info);
0846     d->iconView->scrollToRelaxed(index);
0847     d->iconView->setSelectedCamItemInfos(CamItemInfoList() << info);
0848 }
0849 
0850 void ImportView::slotImageChangeFailed(const QString& message, const QStringList& fileNames)
0851 {
0852     if (fileNames.isEmpty())
0853     {
0854         return;
0855     }
0856 
0857     DMessageBox::showInformationList(QMessageBox::Critical,
0858                                      qApp->activeWindow(),
0859                                      qApp->applicationName(),
0860                                      message,
0861                                      fileNames);
0862 }
0863 
0864 bool ImportView::hasCurrentItem() const
0865 {
0866     // We should actually get this directly from the selection model,
0867     // but the iconView is fine for now.
0868 
0869     return !d->iconView->currentInfo().isNull();
0870 }
0871 
0872 /*
0873 void ImportView::slotImageExifOrientation(int orientation)
0874 {
0875     FileActionMngr::instance()->setExifOrientation(d->iconView->selectedCamItemInfos(), orientation);
0876 }
0877 */
0878 
0879 ImportFilterModel* ImportView::importFilterModel() const
0880 {
0881     return d->iconView->importFilterModel();
0882 }
0883 
0884 ImportStackedView::StackedViewMode ImportView::viewMode() const
0885 {
0886     return d->stackedView->viewMode();
0887 }
0888 
0889 void ImportView::toggleFullScreen(bool set)
0890 {
0891     d->stackedView->importPreviewView()->toggleFullScreen(set);
0892 }
0893 
0894 void ImportView::updateIconView()
0895 {
0896     d->iconView->viewport()->update();
0897 }
0898 
0899 } // namespace Digikam
0900 
0901 #include "moc_importview.cpp"