File indexing completed on 2025-04-27 03:58:10

0001 /* ============================================================
0002  *
0003  * This file is a part of digiKam project
0004  * https://www.digikam.org
0005  *
0006  * Date        : 2007-06-05
0007  * Description : Thumbnail loading - private containers
0008  *
0009  * SPDX-FileCopyrightText: 2006-2011 by Marcel Wiesweg <marcel dot wiesweg at gmx dot de>
0010  * SPDX-FileCopyrightText: 2005-2024 by Gilles Caulier <caulier dot gilles at gmail dot com>
0011  * SPDX-FileCopyrightText: 2015      by Mohamed_Anwer <m_dot_anwer at gmx dot com>
0012  *
0013  * SPDX-License-Identifier: GPL-2.0-or-later
0014  *
0015  * ============================================================ */
0016 
0017 #include "thumbnailloadthread_p.h"
0018 
0019 namespace Digikam
0020 {
0021 
0022 bool ThumbnailLoadThread::Private::hasHighlightingBorder() const
0023 {
0024     return (highlight && (size >= 10));
0025 }
0026 
0027 int ThumbnailLoadThread::Private::pixmapSizeForThumbnailSize(int thumbnailSize) const
0028 {
0029     if (hasHighlightingBorder())
0030     {
0031         return (thumbnailSize + 2);
0032     }
0033 
0034     return thumbnailSize;
0035 }
0036 
0037 int ThumbnailLoadThread::Private::thumbnailSizeForPixmapSize(int pixmapSize) const
0038 {
0039     // Bug #206666: Do not cut off one-pixel line for highlighting border
0040 
0041     if (hasHighlightingBorder())
0042     {
0043         return (pixmapSize - 2);
0044     }
0045 
0046     return pixmapSize;
0047 }
0048 
0049 bool ThumbnailLoadThread::Private::checkDescription(const LoadingDescription& description)
0050 {
0051     QString cacheKey = description.cacheKey();
0052 
0053     {
0054         LoadingCache* const cache = LoadingCache::cache();
0055         LoadingCache::CacheLock lock(cache);
0056 
0057         if (cache->hasThumbnailPixmap(cacheKey))
0058         {
0059             return false;
0060         }
0061     }
0062 
0063     {
0064         QMutexLocker lock(&resultsMutex);
0065 
0066         if (collectedResults.contains(cacheKey))
0067         {
0068             return false;
0069         }
0070     }
0071 
0072     return true;
0073 }
0074 
0075 QList<LoadingDescription> ThumbnailLoadThread::Private::makeDescriptions(const QList<ThumbnailIdentifier>& identifiers, int size)
0076 {
0077     QList<LoadingDescription> descriptions;
0078     {
0079         LoadingDescription description = createLoadingDescription(ThumbnailIdentifier(), size, false);
0080 
0081         Q_FOREACH (const ThumbnailIdentifier& identifier, identifiers)
0082         {
0083             description.filePath = identifier.filePath;
0084             description.previewParameters.storageReference = identifier.id;
0085 
0086             if (!checkDescription(description))
0087             {
0088                 continue;
0089             }
0090 
0091             descriptions << description;
0092         }
0093     }
0094 
0095     lastDescriptions = descriptions;
0096 
0097     return descriptions;
0098 }
0099 
0100 QList<LoadingDescription> ThumbnailLoadThread::Private::makeDescriptions(const QList<QPair<ThumbnailIdentifier, QRect> >& identifiersAndRects, int size)
0101 {
0102     QList<LoadingDescription> descriptions;
0103     {
0104         LoadingDescription description = createLoadingDescription(ThumbnailIdentifier(), size, QRect(1, 1, 1, 1), false);
0105         typedef QPair<ThumbnailIdentifier, QRect> IdRectPair;
0106 
0107         Q_FOREACH (const IdRectPair& pair, identifiersAndRects)
0108         {
0109             description.filePath                           = pair.first.filePath;
0110             description.previewParameters.storageReference = pair.first.id;
0111 
0112             if (!checkDescription(description))
0113             {
0114                 continue;
0115             }
0116 
0117             description.previewParameters.extraParameter = pair.second;
0118             descriptions << description;
0119         }
0120     }
0121 
0122     lastDescriptions = descriptions;
0123 
0124     return descriptions;
0125 }
0126 
0127 void ThumbnailImageCatcher::Private::reset()
0128 {
0129     intermediate.clear();
0130     tasks.clear();
0131 
0132     if (active)
0133     {
0134         state = Accepting;
0135     }
0136     else
0137     {
0138         state = Inactive;
0139     }
0140 }
0141 
0142 void ThumbnailImageCatcher::Private::harvest(const LoadingDescription& description, const QImage& image)
0143 {
0144     // called under lock
0145 
0146     bool finished = true;
0147 
0148     for (int i = 0 ; i < tasks.size() ; ++i)
0149     {
0150         Private::CatcherResult& task = tasks[i];
0151 
0152         if (task.description == description)
0153         {
0154             task.image    = image;
0155             task.received = true;
0156         }
0157 
0158         finished = (finished && task.received);
0159     }
0160 
0161     // cppcheck-suppress knownConditionTrueFalse
0162     if (finished)
0163     {
0164         state = Quitting;
0165         condVar.wakeOne();
0166     }
0167 }
0168 
0169 } // namespace Digikam