1 /* ============================================================
2 *
3 * This file is a part of digiKam project
4 * https://www.digikam.org
5 *
6 * Date : 2005-04-21
7 * Description : Handling access to one item and associated data
8 *
9 * Copyright (C) 2005 by Renchi Raju <renchi dot raju at gmail dot com>
10 * Copyright (C) 2007-2013 by Marcel Wiesweg <marcel dot wiesweg at gmx dot de>
11 * Copyright (C) 2009-2021 by Gilles Caulier <caulier dot gilles at gmail dot com>
12 * Copyright (C) 2013 by Michael G. Hansen <mike at mghansen dot de>
13 *
14 * This program is free software; you can redistribute it
15 * and/or modify it under the terms of the GNU General
16 * Public License as published by the Free Software Foundation;
17 * either version 2, or (at your option)
18 * any later version.
19 *
20 * This program is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
24 *
25 * ============================================================ */
26
27 #ifndef DIGIKAM_ITEM_INFO_H
28 #define DIGIKAM_ITEM_INFO_H
29
30 // Qt includes
31
32 #include <QUrl>
33 #include <QList>
34 #include <QSize>
35 #include <QString>
36 #include <QDateTime>
37 #include <QExplicitlySharedDataPointer>
38
39 // Local includes
40
41 #include "digikam_export.h"
42 #include "coredbalbuminfo.h"
43 #include "coredburl.h"
44 #include "coredbfields.h"
45 #include "iteminfolist.h"
46
47 namespace Digikam
48 {
49
50 class DImageHistory;
51 class HistoryImageId;
52 class ItemComments;
53 class ImageCommonContainer;
54 class ItemCopyright;
55 class ItemExtendedProperties;
56 class ItemInfoData;
57 class ItemListerRecord;
58 class ImageMetadataContainer;
59 class VideoMetadataContainer;
60 class ItemPosition;
61 class ItemTagPair;
62 class PhotoInfoContainer;
63 class VideoInfoContainer;
64 class Template;
65 class ThumbnailIdentifier;
66 class ThumbnailInfo;
67
68 /**
69 * The ItemInfo class contains provides access to the database for a single image.
70 * The properties can be read and written. Information will be cached.
71 *
72 * NOTE: access rules for all methods in this class:
73 * ItemInfoData members shall be accessed only under CoreDbAccess lock.
74 * The id and albumId are the exception to this rule, as they are
75 * primitive and will never change during the lifetime of an object.
76 */
77 class DIGIKAM_DATABASE_EXPORT ItemInfo
78 {
79 public:
80
81 typedef DatabaseFields::Hash<QVariant> DatabaseFieldsHashRaw;
82
83 public:
84
85 /**
86 * Constructor
87 * Creates a null image info
88 */
89 ItemInfo();
90
91 /**
92 * Constructor. Creates an ItemInfo object without any cached data initially.
93 * @param ID the unique ID for this image
94 */
95 explicit ItemInfo(qlonglong ID);
96
97 /**
98 * Constructor. Creates an ItemInfo object where the provided information
99 * will initially be available cached, without database access.
100 */
101 explicit ItemInfo(const ItemListerRecord& record);
102
103 /**
104 * Copy constructor.
105 */
106 ItemInfo(const ItemInfo& info);
107
108 /**
109 * Destructor
110 */
111 ~ItemInfo();
112
113 /**
114 * Creates an ItemInfo object from a file url.
115 */
116 static ItemInfo fromLocalFile(const QString& path);
117 static ItemInfo fromUrl(const QUrl& url);
118
119 /**
120 * Create an ItemInfo object from the given combination, which
121 * must be cleaned and corresponding to the values in the database
122 */
123 static ItemInfo fromLocationAlbumAndName(int locationId, const QString& album, const QString& name);
124
125 ItemInfo& operator=(const ItemInfo& info);
126
127 bool operator==(const ItemInfo& info) const;
128 bool operator!=(const ItemInfo& info) const;
129 bool operator<(const ItemInfo& info) const;
130
131 /**
132 * Copy database information of this item to a newly created item
133 * @param dstAlbumID destination album id
134 * @param dstFileName new filename
135 * @return an ItemInfo object of the new item
136 */
137 ItemInfo copyItem(int dstAlbumID, const QString& dstFileName);
138
139 /**
140 * Returns true if this is a valid ItemInfo,
141 * and the location of the image is currently available
142 * (information freshly obtained from CollectionManager)
143 */
144 bool isLocationAvailable() const;
145
146 public:
147
148 // -----------------------------------------------------------------------------
149
150 /** @name Operations with Properties
151 */
152
153 //@{
154
155 /**
156 * Returns if this objects contains valid data
157 */
158 bool isNull() const;
159
160 /**
161 * @return the name of the image
162 */
163 QString name() const;
164
165 /**
166 * @return the datetime of the image
167 */
168 QDateTime dateTime() const;
169
170 /**
171 * @return the modification datetime of the image
172 */
173 QDateTime modDateTime() const;
174
175 /**
176 * @return the filesize of the image
177 */
178 qlonglong fileSize() const;
179
180 /**
181 * @return the dimensions of the image (valid only if dimensions
182 * have been requested)
183 */
184 QSize dimensions() const;
185
186 /**
187 * Returns the file:// url.
188 * This is equivalent to QUrl::fromLocalFile(filePath())
189 */
190 QUrl fileUrl() const;
191
192 /**
193 * Returns the file path to the image
194 */
195 QString filePath() const;
196
197 /**
198 * @return the unique image id for this item
199 */
200 qlonglong id() const;
201
202 /**
203 * @return the id of the PAlbum to which this item belongs
204 */
205 int albumId() const;
206
207 /**
208 * The album root id
209 */
210 int albumRootId() const;
211
212 /**
213 * @return the id of the Aspect Ratio for this item
214 */
215 double aspectRatio() const;
216
217 /**
218 * Returns the manual sort order
219 */
220 qlonglong manualOrder() const;
221
222 /**
223 * Returns the category of the item: Image, Audio, Video
224 */
225 DatabaseItem::Category category() const;
226
227 /**
228 * Returns the image format / mimetype as a standardized
229 * string (see project/documents/DBSCHEMA.ODS).
230 */
231 QString format() const;
232
233 /**
234 * Returns true if the image is marked as visible in the database.
235 */
236 bool isVisible() const;
237
238 /**
239 * Returns true if the corresponding file was not deleted.
240 */
241 bool isRemoved() const;
242
243 /**
244 * Returns the orientation of the image,
245 * (MetaEngine::ImageOrientation, EXIF standard)
246 */
247 int orientation() const;
248
249 /**
250 * @return the default title for this item
251 */
252 QString title() const;
253
254 /**
255 * @return the default comment for this item
256 */
257 QString comment() const;
258
259 /**
260 * @return the number of Unconfirmed Faces in this item.
261 */
262 int unconfirmedFaceCount() const;
263
264 /**
265 * @return the map of Tag Region (in XML form) to Suggested Names for all
266 * Faces in the Image.
267 * Used to categorize images based on Face Suggestions.
268 */
269 QMap<QString, QString> getSuggestedNames() const;
270
271 /**
272 * Set the name (write it to database)
273 * @param newName the new name.
274 */
275 void setName(const QString& newName);
276
277 /**
278 * Set the date and time (write it to database)
279 * @param dateTime the new date and time.
280 */
281 void setDateTime(const QDateTime& dateTime);
282
283 /**
284 * Set the modification date and time (write it to database)
285 * @param dateTime the new modification date and time.
286 */
287 void setModDateTime(const QDateTime& dateTime);
288
289 /**
290 * Set the manual sorting order for the item
291 */
292 void setManualOrder(qlonglong value);
293
294 /**
295 * Set the orientation for the item
296 */
297 void setOrientation(int value);
298
299 /**
300 * Set the visibility flag - triggers between Visible and Hidden
301 */
302 void setVisible(bool isVisible);
303
304 /**
305 * @todo Supports only VideoMetadataField and ImageMetadataField values for now.
306 */
307 DatabaseFieldsHashRaw getDatabaseFieldsRaw(const DatabaseFields::Set& requestedSet) const;
308 QVariant getDatabaseFieldRaw(const DatabaseFields::Set& requestedField) const;
309
310 //@}
311
312 public:
313
314 // -----------------------------------------------------------------------------
315
316 /** @name Operations with Geolocation
317 */
318
319 //@{
320
321 /**
322 * Retrieve the ItemPosition object for this item.
323 */
324 ItemPosition imagePosition() const;
325
326 /**
327 * Retrieves the coordinates and the altitude.
328 * Returns 0 if hasCoordinates(), or hasAltitude resp, is false.
329 */
330 double longitudeNumber() const;
331 double latitudeNumber() const;
332 double altitudeNumber() const;
333 bool hasCoordinates() const;
334 bool hasAltitude() const;
335
336 //@}
337
338 public:
339
340 // -----------------------------------------------------------------------------
341
342 /** @name Operations with History
343 */
344
345 //@{
346
347 /**
348 * Retrieves and sets the image history from the database.
349 * Note: The image history retrieved here does typically include all
350 * steps from the original to this image, but does not reference this image
351 * itself.
352 */
353 DImageHistory imageHistory() const;
354 void setItemHistory(const DImageHistory& history);
355 bool hasImageHistory() const;
356
357 /**
358 * Retrieves and sets this' images UUID
359 */
360 QString uuid() const;
361 void setUuid(const QString& uuid);
362
363 /**
364 * Constructs a HistoryImageId with all available information for this image.
365 */
366 HistoryImageId historyImageId() const;
367
368 /**
369 * Retrieve information about images from which this image
370 * is derived (ancestorImages) and images that have been derived
371 * from this images (derivedImages).
372 */
373 bool hasDerivedImages() const;
374 bool hasAncestorImages() const;
375
376 QList<ItemInfo> derivedImages() const;
377 QList<ItemInfo> ancestorImages() const;
378
379 /**
380 * Returns the cloud of all directly or indirectly related images,
381 * derived images or ancestors, in from of "a derived from b" pairs.
382 */
383 QList<QPair<qlonglong, qlonglong> > relationCloud() const;
384
385 /**
386 * Add a relation to the database:
387 * This image is derived from the ancestorImage.
388 */
389 void markDerivedFrom(const ItemInfo& ancestorImage);
390
391 //@}
392
393 public:
394
395 // -----------------------------------------------------------------------------
396
397 /** @name Operations with Groups
398 */
399
400 //@{
401
402 /**
403 * The image is grouped in the group of another (leading) image.
404 */
405 bool isGrouped() const;
406 /**
407 * The image is the leading image of a group,
408 * there are other images grouped behind this one.
409 */
410 bool hasGroupedImages() const;
411 int numberOfGroupedImages() const;
412
413 /**
414 * Returns the leading image of the group.
415 * Returns a null image if this image is not grouped (isGrouped())
416 */
417 ItemInfo groupImage() const;
418 qlonglong groupImageId() const;
419
420 /**
421 * Returns the list of images grouped behind this image (not including this
422 * image itself) and an empty list if there is none.
423 */
424 QList<ItemInfo> groupedImages() const;
425
426 /**
427 * Group this image behind the given image
428 */
429 void addToGroup(const ItemInfo& info);
430
431 /**
432 * This image is grouped behind another image:
433 * Remove this image from its group
434 */
435 void removeFromGroup();
436
437 /**
438 * This image hasGroupedImages(): Split up the group,
439 * remove all groupedImages() from this image's group.
440 */
441 void clearGroup();
442
443 //@}
444
445 public:
446
447 // -----------------------------------------------------------------------------
448
449 /** @name Operations with Containers
450 */
451
452 //@{
453
454 /**
455 * Retrieve information about the image,
456 * in form of numbers and user presentable strings,
457 * for certain defined fields of information (see databaseinfocontainers.h)
458 */
459 ImageCommonContainer imageCommonContainer() const;
460 ImageMetadataContainer imageMetadataContainer() const;
461 VideoMetadataContainer videoMetadataContainer() const;
462 PhotoInfoContainer photoInfoContainer() const;
463 VideoInfoContainer videoInfoContainer() const;
464
465 /**
466 * Retrieve metadata template information about the image.
467 */
468 Template metadataTemplate() const;
469
470 /**
471 * Set metadata template information (write it to database)
472 * @param t the new template data.
473 */
474 void setMetadataTemplate(const Template& t);
475
476 /**
477 * Remove all template info about the image from database.
478 */
479 void removeMetadataTemplate();
480
481 /**
482 * Retrieve the ItemComments object for this item.
483 * This object allows full read and write access to all comments
484 * and their properties.
485 * You need to hold CoreDbAccess to ensure the validity.
486 * For simple, cached read access see comment().
487 */
488 ItemComments imageComments(CoreDbAccess& access) const;
489
490 /**
491 * Retrieve the ItemCopyright object for this item.
492 * This object allows full read and write access to all copyright
493 * values.
494 */
495 ItemCopyright imageCopyright() const;
496
497 /**
498 * Retrieve the ItemExtendedProperties object for this item.
499 * This object allows full read and write access to all extended properties
500 * values.
501 */
502 ItemExtendedProperties imageExtendedProperties() const;
503
504 //@}
505
506 public:
507
508 // -----------------------------------------------------------------------------
509
510 /** @name Operations with Tags
511 */
512
513 //@{
514
515 /**
516 * Adds a tag to the item (writes it to database)
517 * @param tagID the ID of the tag to add
518 */
519 void setTag(int tagID);
520
521 /**
522 * Adds tags in the list to the item.
523 * Tags are created if they do not yet exist
524 */
525 void addTagPaths(const QStringList& tagPaths);
526
527 /**
528 * Remove a tag from the item (removes it from database)
529 * @param tagID the ID of the tag to remove
530 */
531 void removeTag(int tagID);
532
533 /**
534 * Remove all tags from the item (removes it from database)
535 */
536 void removeAllTags();
537
538 /**
539 * Retrieve an ItemTagPair object for a single tag, or for all
540 * image/tag pairs for which properties are available
541 * (not necessarily the assigned tags)
542 */
543 ItemTagPair imageTagPair(int tagId) const;
544 QList<ItemTagPair> availableItemTagPairs() const;
545
546 /**
547 * @return a list of IDs of tags assigned to this item
548 * @see tagNames
549 * @see tagPaths
550 * @see Album::id()
551 */
552 QList<int> tagIds() const;
553
554 private:
555
556 void loadTagIds() const;
557
558 //@}
559
560 public:
561
562 // -----------------------------------------------------------------------------
563
564 /**
565 * @name Operations with Labels
566 */
567
568 //@{
569
570 /**
571 * Returns the Pick Label Id (see PickLabel values in globals.h)
572 */
573 int pickLabel() const;
574
575 /**
576 * Returns the Color Label Id (see ColorLabel values in globals.h)
577 */
578 int colorLabel() const;
579
580 /**
581 * Returns the rating
582 */
583 int rating() const;
584
585 /**
586 * Set the pick Label Id for the item (see PickLabel values from globals.h)
587 */
588 void setPickLabel(int value);
589
590 /**
591 * Set the color Label Id for the item (see ColorLabel values from globals.h)
592 */
593 void setColorLabel(int value);
594
595 /**
596 * Set the rating for the item
597 */
598 void setRating(int value);
599
600 //@}
601
602 public:
603
604 // -----------------------------------------------------------------------------
605
606 /**
607 * @name Operations with Thumbnails
608 */
609
610 //@{
611
612 /**
613 * Fills a ThumbnailIdentifier / ThumbnailInfo from this ItemInfo
614 */
615 ThumbnailIdentifier thumbnailIdentifier() const;
616 ThumbnailInfo thumbnailInfo() const;
617 static ThumbnailIdentifier thumbnailIdentifier(qlonglong id);
618
619 //@}
620
621 public:
622
623 // -----------------------------------------------------------------------------
624
625 /**
626 * @name Operations with Similarity
627 */
628
629 //@{
630
631 double similarityTo(const qlonglong imageId) const;
632 double currentSimilarity() const;
633
634 /**
635 * Returns the id of the current fuzzy search reference image.
636 */
637 qlonglong currentReferenceImage() const;
638
639 /**
640 * Return a signature for the item.
641 */
642 uint hash() const;
643
644 /**
645 * Scans the database for items with the given signature.
646 */
647 QList<ItemInfo> fromUniqueHash(const QString& uniqueHash, qlonglong fileSize);
648
649 /**
650 * @return the unique hash signature as string of the image.
651 */
652 QString uniqueHash() const;
653
654 //@}
655
656 private:
657
658 friend class ItemInfoCache;
659 friend class ItemInfoList;
660
661 QExplicitlySharedDataPointer<ItemInfoData> m_data;
662 };
663
qHash(const ItemInfo & info)664 inline uint qHash(const ItemInfo& info)
665 {
666 return info.hash();
667 }
668
669 //! qDebug() stream operator. Writes property @a info to the debug output in a nicely formatted way.
670 DIGIKAM_DATABASE_EXPORT QDebug operator<<(QDebug stream, const ItemInfo& info);
671
672 } // namespace Digikam
673
674 Q_DECLARE_TYPEINFO(Digikam::ItemInfo, Q_MOVABLE_TYPE);
675 Q_DECLARE_METATYPE(Digikam::ItemInfo)
676
677 #endif // DIGIKAM_ITEM_INFO_H
678