File indexing completed on 2025-01-05 03:51:11
0001 /* ============================================================ 0002 * 0003 * This file is a part of digiKam project 0004 * https://www.digikam.org 0005 * 0006 * Date : 2010-02-06 0007 * Description : Thumbnail bar for items 0008 * 0009 * SPDX-FileCopyrightText: 2009-2011 by Marcel Wiesweg <marcel dot wiesweg at gmx dot de> 0010 * SPDX-FileCopyrightText: 2009-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 "itemthumbnailbar.h" 0017 0018 // Qt includes 0019 0020 #include <QEvent> 0021 0022 // Local includes 0023 0024 #include "digikam_debug.h" 0025 #include "applicationsettings.h" 0026 #include "itemalbumfiltermodel.h" 0027 #include "itemalbummodel.h" 0028 #include "itemdragdrop.h" 0029 #include "itemratingoverlay.h" 0030 #include "itemcoordinatesoverlay.h" 0031 #include "itemthumbnaildelegate.h" 0032 #include "fileactionmngr.h" 0033 0034 namespace Digikam 0035 { 0036 0037 class Q_DECL_HIDDEN ItemThumbnailBar::Private 0038 { 0039 public: 0040 0041 explicit Private() 0042 : scrollPolicy (Qt::ScrollBarAlwaysOn), 0043 duplicatesFilter(nullptr) 0044 { 0045 } 0046 0047 Qt::ScrollBarPolicy scrollPolicy; 0048 NoDuplicatesItemFilterModel* duplicatesFilter; 0049 }; 0050 0051 ItemThumbnailBar::ItemThumbnailBar(QWidget* const parent) 0052 : ItemCategorizedView(parent), 0053 d (new Private()) 0054 { 0055 setItemDelegate(new ItemThumbnailDelegate(this)); 0056 setSpacing(3); 0057 setUsePointingHandCursor(false); 0058 setScrollStepGranularity(5); 0059 setScrollBarPolicy(Qt::ScrollBarAlwaysOn); 0060 0061 setDragEnabled(true); 0062 setAcceptDrops(true); 0063 setDropIndicatorShown(false); 0064 0065 // Disable QListView::Batched optimization 0066 // for the thumbnail bar, see bug #468593 0067 0068 setLayoutMode(QListView::SinglePass); 0069 0070 setScrollCurrentToCenter(ApplicationSettings::instance()->getScrollItemToCenter()); 0071 setToolTipEnabled(ApplicationSettings::instance()->showToolTipsIsValid()); 0072 0073 // --- NOTE: use dynamic binding as slotSetupChanged() is a virtual slot which can be re-implemented in derived classes. 0074 connect(ApplicationSettings::instance(), &ApplicationSettings::setupChanged, 0075 this, &ItemThumbnailBar::slotSetupChanged); 0076 0077 this->slotSetupChanged(); 0078 // --- 0079 0080 setFlow(LeftToRight); 0081 } 0082 0083 ItemThumbnailBar::~ItemThumbnailBar() 0084 { 0085 delete d; 0086 } 0087 0088 void ItemThumbnailBar::setModelsFiltered(ItemModel* model, ImageSortFilterModel* filterModel) 0089 { 0090 if (!d->duplicatesFilter) 0091 { 0092 d->duplicatesFilter = new NoDuplicatesItemFilterModel(this); 0093 } 0094 0095 d->duplicatesFilter->setSourceFilterModel(filterModel); 0096 ItemCategorizedView::setModels(model, d->duplicatesFilter); 0097 } 0098 0099 void ItemThumbnailBar::installOverlays() 0100 { 0101 ItemRatingOverlay* const ratingOverlay = new ItemRatingOverlay(this); 0102 addOverlay(ratingOverlay); 0103 0104 connect(ratingOverlay, SIGNAL(ratingEdited(QList<QModelIndex>,int)), 0105 this, SLOT(assignRating(QList<QModelIndex>,int))); 0106 0107 addOverlay(new ItemCoordinatesOverlay(this)); 0108 } 0109 0110 void ItemThumbnailBar::slotDockLocationChanged(Qt::DockWidgetArea area) 0111 { 0112 if (area == Qt::LeftDockWidgetArea || area == Qt::RightDockWidgetArea) 0113 { 0114 setFlow(TopToBottom); 0115 } 0116 else 0117 { 0118 setFlow(LeftToRight); 0119 } 0120 0121 scrollTo(currentIndex()); 0122 } 0123 0124 void ItemThumbnailBar::setScrollBarPolicy(Qt::ScrollBarPolicy policy) 0125 { 0126 if (policy == Qt::ScrollBarAsNeeded) 0127 { 0128 // Delegate resizing will cause endless relayouting, see bug #228807 0129 qCDebug(DIGIKAM_GENERAL_LOG) << "The Qt::ScrollBarAsNeeded policy is not supported by ItemThumbnailBar"; 0130 } 0131 0132 d->scrollPolicy = policy; 0133 0134 if (flow() == TopToBottom) 0135 { 0136 setVerticalScrollBarPolicy(d->scrollPolicy); 0137 setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); 0138 } 0139 else 0140 { 0141 setHorizontalScrollBarPolicy(d->scrollPolicy); 0142 setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff); 0143 } 0144 } 0145 0146 void ItemThumbnailBar::setFlow(QListView::Flow flow) 0147 { 0148 setWrapping(false); 0149 0150 ItemCategorizedView::setFlow(flow); 0151 0152 ItemThumbnailDelegate* const del = static_cast<ItemThumbnailDelegate*>(delegate()); 0153 del->setFlow(flow); 0154 0155 // Reset the minimum and maximum sizes. 0156 setMinimumSize(QSize(0, 0)); 0157 setMaximumSize(QSize(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX)); 0158 0159 // Adjust minimum and maximum width to thumbnail sizes. 0160 if (flow == TopToBottom) 0161 { 0162 int viewportFullWidgetOffset = size().width() - viewport()->size().width(); 0163 setMinimumWidth(del->minimumSize() + viewportFullWidgetOffset); 0164 setMaximumWidth(del->maximumSize() + viewportFullWidgetOffset); 0165 } 0166 else 0167 { 0168 int viewportFullWidgetOffset = size().height() - viewport()->size().height(); 0169 setMinimumHeight(del->minimumSize() + viewportFullWidgetOffset); 0170 setMaximumHeight(del->maximumSize() + viewportFullWidgetOffset); 0171 } 0172 0173 setScrollBarPolicy(d->scrollPolicy); 0174 } 0175 0176 void ItemThumbnailBar::slotSetupChanged() 0177 { 0178 setScrollCurrentToCenter(ApplicationSettings::instance()->getScrollItemToCenter()); 0179 setToolTipEnabled(ApplicationSettings::instance()->showToolTipsIsValid()); 0180 setFont(ApplicationSettings::instance()->getIconViewFont()); 0181 0182 ItemCategorizedView::slotSetupChanged(); 0183 } 0184 0185 void ItemThumbnailBar::assignRating(const QList<QModelIndex>& indexes, int rating) 0186 { 0187 ItemInfoList infos(imageSortFilterModel()->imageInfos(indexes)); 0188 0189 if (needGroupResolving(ApplicationSettings::Metadata, infos)) 0190 { 0191 infos = resolveGrouping(infos); 0192 } 0193 0194 FileActionMngr::instance()->assignRating(infos, rating); 0195 } 0196 0197 bool ItemThumbnailBar::event(QEvent* e) 0198 { 0199 // reset widget max/min sizes 0200 if (e->type() == QEvent::StyleChange || e->type() == QEvent::Show) 0201 { 0202 setFlow(flow()); 0203 } 0204 0205 return ItemCategorizedView::event(e); 0206 } 0207 0208 QModelIndex ItemThumbnailBar::nextIndex(const QModelIndex& index) const 0209 { 0210 return imageFilterModel()->index(index.row() + 1, 0); 0211 } 0212 0213 QModelIndex ItemThumbnailBar::previousIndex(const QModelIndex& index) const 0214 { 0215 return imageFilterModel()->index(index.row() - 1, 0); 0216 } 0217 0218 QModelIndex ItemThumbnailBar::firstIndex() const 0219 { 0220 return imageFilterModel()->index(0, 0); 0221 } 0222 0223 QModelIndex ItemThumbnailBar::lastIndex() const 0224 { 0225 return imageFilterModel()->index(imageFilterModel()->rowCount() - 1, 0); 0226 } 0227 0228 bool ItemThumbnailBar::hasHiddenGroupedImages(const ItemInfo& info) const 0229 { 0230 return (info.hasGroupedImages() && 0231 !imageFilterModel()->isAllGroupsOpen() && 0232 !imageFilterModel()->isGroupOpen(info.id())); 0233 } 0234 0235 } // namespace Digikam 0236 0237 #include "moc_itemthumbnailbar.cpp"