File indexing completed on 2024-05-05 04:33:15

0001 /*
0002     SPDX-FileCopyrightText: 2004-2018 Gilles Caulier <caulier dot gilles at gmail dot com>
0003     SPDX-FileCopyrightText: 2006-2012 Marcel Wiesweg <marcel dot wiesweg at gmx dot de>
0004     SPDX-FileCopyrightText: 2004-2005 Renchi Raju <renchi dot raju at gmail dot com>
0005     SPDX-FileCopyrightText: 2004-2005 Jesper K. Pedersen <blackie at kde dot org>
0006     SPDX-FileCopyrightText: 2004-2005 Aurelien Gateau <aurelien dot gateau at free dot fr>
0007 
0008     SPDX-License-Identifier: GPL-2.0-or-later
0009 */
0010 
0011 #include "interface.h"
0012 
0013 // Qt includes
0014 
0015 #include <QPixmap>
0016 #include <QImageReader>
0017 #include <QImageWriter>
0018 #include <QDir>
0019 
0020 // Local includes
0021 
0022 #include "libkipi_version.h"
0023 #include "libkipi_debug.h"
0024 #include "imageinfo.h"
0025 #include "imagecollection.h"
0026 #include "imagecollectionselector.h"
0027 #include "imageinfoshared.h"
0028 #include "pluginloader.h"
0029 #include "uploadwidget.h"
0030 
0031 // Macros
0032 
0033 #define PrintWarningMessageFeature(feature)                                                       \
0034         qCWarning(LIBKIPI_LOG) << "This should only be invoked if the host application supports " \
0035                                   "KIPI::Features (" << feature << "). If host application do "   \
0036                                   "support that, then this function should have been overridden " \
0037                                   "in the KIPI host interface."
0038 
0039 #define PrintWarningMessage() qCWarning(LIBKIPI_LOG) << "This method should have been overridden in the kipi host interface."
0040 
0041 inline void initLibkipiResource()
0042 {
0043     Q_INIT_RESOURCE(libkipi);
0044 }
0045 
0046 namespace KIPI
0047 {
0048 
0049 Interface::Interface(QObject* const parent, const QString& name)
0050     : QObject(parent)
0051 {
0052     initLibkipiResource();
0053 
0054     setObjectName(name);
0055 }
0056 
0057 Interface::~Interface()
0058 {
0059 }
0060 
0061 QString Interface::version()
0062 {
0063     return QString::fromLatin1(KIPI_VERSION_STRING);
0064 }
0065 
0066 void Interface::refreshImages(const QList<QUrl>&)
0067 {
0068     PrintWarningMessage();
0069 }
0070 
0071 bool Interface::hasFeature(Features feature) const
0072 {
0073     return (features() & feature) != 0;
0074 }
0075 
0076 bool Interface::hasFeature( const QString& feature ) const
0077 {
0078     if       ( feature == QString::fromLatin1("CollectionsHaveComments" ))
0079         return hasFeature( CollectionsHaveComments );
0080     else if  ( feature == QString::fromLatin1("CollectionsHaveCategory" ))
0081         return hasFeature( CollectionsHaveCategory );
0082     else if  ( feature == QString::fromLatin1("CollectionsHaveCreationDate" ))
0083         return hasFeature( CollectionsHaveCreationDate );
0084     else if  ( feature == QString::fromLatin1("ImagesHasComments" ))
0085         return hasFeature( ImagesHasComments );
0086     else if  ( feature == QString::fromLatin1("ImagesHasTime" ))
0087         return hasFeature( ImagesHasTime );
0088     else if  ( feature == QString::fromLatin1("ImagesHasTitlesWritable" ))
0089         return hasFeature( ImagesHasTitlesWritable );
0090     else if  ( feature == QString::fromLatin1("HostSupportsThumbnails" ))
0091         return hasFeature( HostSupportsThumbnails );
0092     else if  ( feature == QString::fromLatin1("HostSupportsReadWriteLock" ))
0093         return hasFeature( HostSupportsReadWriteLock );
0094     else if  ( feature == QString::fromLatin1("HostSupportsDateRanges" ))
0095         return hasFeature( HostSupportsDateRanges );
0096     else if  ( feature == QString::fromLatin1("HostAcceptNewImages" ))
0097         return hasFeature( HostAcceptNewImages );
0098     else if  ( feature == QString::fromLatin1("HostSupportsProgressBar" ))
0099         return hasFeature( HostSupportsProgressBar );
0100     else if  ( feature == QString::fromLatin1("HostSupportsTags" ))
0101         return hasFeature( HostSupportsTags );
0102     else if  ( feature == QString::fromLatin1("HostSupportsRating" ))
0103         return hasFeature( HostSupportsRating );
0104     else if  ( feature == QString::fromLatin1("HostSupportsPickLabel" ))
0105         return hasFeature( HostSupportsPickLabel );
0106     else if  ( feature == QString::fromLatin1("HostSupportsColorLabel" ))
0107         return hasFeature( HostSupportsColorLabel );
0108     else if  ( feature == QString::fromLatin1("HostSupportsItemReservation" ))
0109         return hasFeature( HostSupportsItemReservation );
0110     else if  ( feature == QString::fromLatin1("HostSupportsPreviews" ))
0111         return hasFeature( HostSupportsPreviews );
0112     else if  ( feature == QString::fromLatin1("HostSupportsRawProcessing" ))
0113         return hasFeature( HostSupportsRawProcessing );
0114     else
0115     {
0116         qCWarning(LIBKIPI_LOG) << "Unknown feature asked for in KIPI::Interface::hasFeature(): " << feature;
0117         return false;
0118     }
0119 }
0120 
0121 bool Interface::addImage(const QUrl&, QString&)
0122 {
0123     PrintWarningMessageFeature("AcceptNewImages");
0124     return false;
0125 }
0126 
0127 void Interface::delImage(const QUrl&)
0128 {
0129     PrintWarningMessage();
0130 }
0131 
0132 ImageCollection Interface::currentAlbum()
0133 {
0134     PrintWarningMessage();
0135     return ImageCollection();
0136 }
0137 
0138 ImageCollection Interface::currentSelection()
0139 {
0140     PrintWarningMessage();
0141     return ImageCollection();
0142 }
0143 
0144 QList<ImageCollection> Interface::allAlbums()
0145 {
0146     PrintWarningMessage();
0147     return QList<ImageCollection>();
0148 }
0149 
0150 int Interface::features() const
0151 {
0152     PrintWarningMessage();
0153     return 0;
0154 }
0155 
0156 void Interface::thumbnail(const QUrl& url, int size)
0157 {
0158     thumbnails(QList<QUrl>() << url, size);
0159 }
0160 
0161 void Interface::thumbnails(const QList<QUrl>& list, int size)
0162 {
0163     Q_UNUSED(size);
0164     PrintWarningMessageFeature("HostSupportsThumbnails");
0165 
0166     for (QList<QUrl>::ConstIterator it = list.begin() ; it != list.end() ; ++it)
0167     {
0168         if ((*it).isValid())
0169             Q_EMIT gotThumbnail((*it), QPixmap());
0170     }
0171 }
0172 
0173 QImage Interface::preview(const QUrl& url)
0174 {
0175     Q_UNUSED(url);
0176     PrintWarningMessageFeature("HostSupportsPreviews");
0177 
0178     return QImage();
0179 }
0180 
0181 bool Interface::saveImage(const QUrl& url, const QString& format,
0182                           const QByteArray& data, uint width, uint height,
0183                           bool  sixteenBit, bool hasAlpha,
0184                           bool* cancel)
0185 {
0186     Q_UNUSED(url);
0187     Q_UNUSED(format);
0188     Q_UNUSED(data);
0189     Q_UNUSED(format);
0190     Q_UNUSED(width);
0191     Q_UNUSED(height);
0192     Q_UNUSED(sixteenBit);
0193     Q_UNUSED(hasAlpha);
0194     Q_UNUSED(cancel);
0195     PrintWarningMessageFeature("HostSupportsSaveImages");
0196     return false;
0197 }
0198 
0199 void Interface::preview(const QUrl& url, int resizedTo)
0200 {
0201     Q_UNUSED(url);
0202     Q_UNUSED(resizedTo);
0203     PrintWarningMessageFeature("HostSupportsPreviews");
0204 
0205     if (url.isValid())
0206         Q_EMIT gotPreview(url, QImage());
0207 }
0208 
0209 QString Interface::rawFiles()
0210 {
0211     PrintWarningMessage();
0212     return QString();
0213 }
0214 
0215 QAbstractItemModel* Interface::getTagTree() const
0216 {
0217     PrintWarningMessage();
0218     return nullptr;
0219 }
0220 
0221 QString Interface::progressScheduled(const QString& title, bool canBeCanceled, bool hasThumb) const
0222 {
0223     PrintWarningMessageFeature("HostSupportsProgressBar");
0224     Q_UNUSED(title);
0225     Q_UNUSED(canBeCanceled);
0226     Q_UNUSED(hasThumb);
0227     return QString();
0228 }
0229 
0230 void Interface::progressValueChanged(const QString& id, float percent)
0231 {
0232     PrintWarningMessageFeature("HostSupportsProgressBar");
0233     Q_UNUSED(id);
0234     Q_UNUSED(percent);
0235 }
0236 
0237 void Interface::progressStatusChanged(const QString& id, const QString& status)
0238 {
0239     PrintWarningMessageFeature("HostSupportsProgressBar");
0240     Q_UNUSED(id);
0241     Q_UNUSED(status);
0242 }
0243 
0244 void Interface::progressThumbnailChanged(const QString& id, const QPixmap& thumb)
0245 {
0246     PrintWarningMessageFeature("HostSupportsProgressBar");
0247     Q_UNUSED(id);
0248     Q_UNUSED(thumb);
0249 }
0250 
0251 void Interface::progressCompleted(const QString& id)
0252 {
0253     PrintWarningMessageFeature("HostSupportsProgressBar");
0254     Q_UNUSED(id);
0255 }
0256 
0257 bool Interface::reserveForAction(const QUrl&, QObject* const, const QString&) const
0258 {
0259     PrintWarningMessageFeature("HostSupportsItemReservation");
0260     return false;
0261 }
0262 
0263 void Interface::clearReservation(const QUrl&, QObject* const)
0264 {
0265     PrintWarningMessageFeature("HostSupportsItemReservation");
0266 }
0267 
0268 bool Interface::itemIsReserved(const QUrl&, QString* const) const
0269 {
0270     PrintWarningMessageFeature("HostSupportsItemReservation");
0271     return false;
0272 }
0273 
0274 FileReadWriteLock* Interface::createReadWriteLock(const QUrl&) const
0275 {
0276     PrintWarningMessageFeature("HostSupportsReadWriteLock");
0277     return nullptr;
0278 }
0279 
0280 MetadataProcessor* Interface::createMetadataProcessor() const
0281 {
0282     PrintWarningMessageFeature("HostSupportsMetadataProcessing");
0283     return nullptr;
0284 }
0285 
0286 void Interface::aboutToEdit(const QUrl&, EditHints)
0287 {
0288 }
0289 
0290 void Interface::editingFinished(const QUrl&, EditHints)
0291 {
0292 }
0293 
0294 QStringList Interface::supportedImageMimeTypes(bool readWrite)
0295 {
0296     QStringList       mimeTypes;
0297     const QList<QByteArray> supported = readWrite ? QImageWriter::supportedMimeTypes()
0298                                                   : QImageReader::supportedMimeTypes();
0299 
0300     for (const QByteArray &mimeType : supported)
0301         mimeTypes.append(QString::fromLatin1(mimeType));
0302 
0303     return mimeTypes;
0304 }
0305 
0306 // -----------------------------------------------------------------------------------------------------------
0307 
0308 FileReadLocker::FileReadLocker(Interface* const iface, const QUrl& url)
0309     : d(iface->createReadWriteLock(url))
0310 {
0311     relock();
0312 }
0313 
0314 FileReadLocker::FileReadLocker(ImageInfoShared* const info)
0315     : d(info->createReadWriteLock())
0316 {
0317     relock();
0318 }
0319 
0320 FileReadLocker::~FileReadLocker()
0321 {
0322     unlock();
0323 }
0324 
0325 FileReadWriteLock* FileReadLocker::fileReadWriteLock() const
0326 {
0327     return d;
0328 }
0329 
0330 void FileReadLocker::relock()
0331 {
0332     if (d)
0333     {
0334         d->lockForRead();
0335     }
0336 }
0337 
0338 void FileReadLocker::unlock()
0339 {
0340     if (d)
0341     {
0342         d->unlock();
0343     }
0344 }
0345 
0346 // -----------------------------------------------------------------------------------------------------------
0347 
0348 FileWriteLocker::FileWriteLocker(Interface* const iface, const QUrl& url)
0349     : d(iface->createReadWriteLock(url))
0350 {
0351     relock();
0352 }
0353 
0354 FileWriteLocker::FileWriteLocker(ImageInfoShared* const info)
0355     : d(info->createReadWriteLock())
0356 {
0357     relock();
0358 }
0359 
0360 FileWriteLocker::~FileWriteLocker()
0361 {
0362     unlock();
0363 }
0364 
0365 FileReadWriteLock* FileWriteLocker::fileReadWriteLock() const
0366 {
0367     return d;
0368 }
0369 
0370 void FileWriteLocker::relock()
0371 {
0372     if (d)
0373     {
0374         d->lockForWrite();
0375     }
0376 }
0377 
0378 void FileWriteLocker::unlock()
0379 {
0380     if (d)
0381     {
0382         d->unlock();
0383     }
0384 }
0385 
0386 // -----------------------------------------------------------------------------------------------------------
0387 
0388 class Q_DECL_HIDDEN EditHintScope::Private
0389 {
0390 
0391 public:
0392 
0393     Private() :
0394         iface(nullptr)
0395     {
0396     }
0397 
0398 public:
0399 
0400     Interface* iface;
0401     QUrl       url;
0402     EditHints  hints;
0403 };
0404 
0405 EditHintScope::EditHintScope(Interface* const iface, const QUrl& url, EditHints hints)
0406     : d(new Private)
0407 {
0408     d->iface = iface;
0409     d->url   = url;
0410     d->hints = hints;
0411 
0412     if (d->iface)
0413     {
0414         d->iface->aboutToEdit(d->url, d->hints);
0415     }
0416 }
0417 
0418 EditHintScope::~EditHintScope()
0419 {
0420     if (d->iface)
0421     {
0422         d->iface->editingFinished(d->url, d->hints);
0423     }
0424 }
0425 
0426 void EditHintScope::changeAborted()
0427 {
0428     d->hints |= HintEditAborted;
0429 }
0430 
0431 } // namespace KIPI
0432 
0433 #include "moc_interface.cpp"