File indexing completed on 2025-01-19 03:56:58
0001 /* ============================================================ 0002 * 0003 * This file is a part of digiKam project 0004 * https://www.digikam.org 0005 * 0006 * Date : 2012-04-19 0007 * Description : time adjust settings container. 0008 * 0009 * SPDX-FileCopyrightText: 2012-2024 by Gilles Caulier <caulier dot gilles at gmail dot com> 0010 * 0011 * SPDX-License-Identifier: GPL-2.0-or-later 0012 * 0013 * ============================================================ */ 0014 0015 #include "timeadjustcontainer.h" 0016 0017 // Qt includes 0018 0019 #include <QRegularExpression> 0020 0021 namespace Digikam 0022 { 0023 0024 TimeAdjustContainer::TimeAdjustContainer() 0025 : customDate (QDateTime::currentDateTime()), 0026 customTime (QDateTime::currentDateTime()), 0027 adjustmentTime(QDateTime()), 0028 updIfAvailable(true), 0029 updEXIFModDate(false), 0030 updEXIFOriDate(false), 0031 updEXIFDigDate(false), 0032 updEXIFThmDate(false), 0033 updIPTCDate (false), 0034 updXMPVideo (false), 0035 updXMPDate (false), 0036 updFileModDate(false), 0037 dateSource (APPDATE), 0038 metadataSource(EXIFIPTCXMP), 0039 fileDateSource(FILELASTMOD), 0040 adjustmentType(COPYVALUE), 0041 adjustmentDays(0) 0042 { 0043 } 0044 0045 TimeAdjustContainer::~TimeAdjustContainer() 0046 { 0047 } 0048 0049 bool TimeAdjustContainer::atLeastOneUpdateToProcess() const 0050 { 0051 return ( 0052 updFileModDate || 0053 updEXIFModDate || 0054 updEXIFOriDate || 0055 updEXIFDigDate || 0056 updEXIFThmDate || 0057 updIPTCDate || 0058 updXMPVideo || 0059 updXMPDate 0060 ); 0061 } 0062 0063 QDateTime TimeAdjustContainer::calculateAdjustedDate(const QDateTime& originalTime, int index) 0064 { 0065 int sign = 0; 0066 QDateTime newTime = originalTime; 0067 0068 int seconds = adjustmentTime.time().second(); 0069 seconds += 60*adjustmentTime.time().minute(); 0070 seconds += 60*60*adjustmentTime.time().hour(); 0071 seconds += 24*60*60*adjustmentDays; 0072 0073 switch (adjustmentType) 0074 { 0075 case ADDVALUE: 0076 sign = 1; 0077 break; 0078 0079 case SUBVALUE: 0080 sign = -1; 0081 break; 0082 0083 case INTERVAL: 0084 { 0085 newTime = newTime.addSecs(index * seconds); 0086 0087 return newTime; 0088 } 0089 default: // COPYVALUE 0090 return originalTime; 0091 } 0092 0093 newTime = newTime.addSecs(sign * seconds); 0094 0095 return newTime; 0096 } 0097 0098 QDateTime TimeAdjustContainer::getDateTimeFromString(const QString& dateStr) const 0099 { 0100 if (dateStr.isEmpty()) 0101 { 0102 return QDateTime(); 0103 } 0104 0105 QStringList regExpStrings; 0106 0107 // Do not change the order of the list. 0108 0109 regExpStrings << QLatin1String("(.*?)([0-9]{4}[-_:\\/]?[0-9]{2}[-_:\\/]?[0-9]{2})" 0110 "(.+)?([0-9]{2}[hH][0-9]{2})(.+)?"); 0111 regExpStrings << QLatin1String("(.*?)([0-9]{8}[T-_ ][0-9]{6})(.+)?"); 0112 regExpStrings << QLatin1String("(.*?)([0-9]{4}[-_:\\/]?[0-9]{2}[-_:\\/]?[0-9]{2})" 0113 "(.+)?([0-9]{2}[-_:.]?[0-9]{2}[-_:.]?[0-9]{2}" 0114 "[-_:.]?[0-9]{3})(.+)?"); 0115 regExpStrings << QLatin1String("(.*?)([0-9]{4}[-_:\\/]?[0-9]{2}[-_:\\/]?[0-9]{2})" 0116 "(.+)?([0-9]{2}[-_:.]?[0-9]{2}[-_:.]?[0-9]{2})(.+)?"); 0117 regExpStrings << QLatin1String("(.*?)([0-9]{2}[-_:\\/.]?[0-9]{2}[-_:\\/.]?[0-9]{4})" 0118 "(.+)?([0-9]{2}[-_:.]?[0-9]{2}[-_:.]?[0-9]{2})(.+)?"); 0119 regExpStrings << QLatin1String("(.*?)([0-9]{2}[-_:\\/.]?[0-9]{2}[-_:\\/.]?[0-9]{4})" 0120 "(.+)?([0-9]{2}[-_:.]?[0-9]{2})(.+)?"); 0121 regExpStrings << QLatin1String("(.*?)([0-9]{2}-[0-9]{2}-[0-9]{2})" 0122 "[ -]?([0-9]{2}[0-9]{2})(.+)?"); 0123 regExpStrings << QLatin1String("(.*?)([0-9]{4}[-_:\\/]?[0-9]{2}[-_:\\/]?[0-9]{2})(.+)?"); 0124 regExpStrings << QLatin1String("(.*?)([0-9]{2}[-_:\\/.]?[0-9]{2}[-_:\\/.]?[0-9]{4})(.+)?"); 0125 regExpStrings << QLatin1String("(.*?)([0-9]{2}[0-9]{2}[0-9]{4})([0-9]{3})(.+)?"); 0126 regExpStrings << QLatin1String("(.*?)([0-9]{2}_[0-9]{2} [0-9]{2})(.+)?"); 0127 0128 QList <QPair<QString, QString> > formatStrings; 0129 formatStrings << qMakePair(QLatin1String("yyyyMMddhhmm"), QString()); 0130 formatStrings << qMakePair(QLatin1String("yyyyMMddhhmmss"), QString()); 0131 formatStrings << qMakePair(QLatin1String("yyyyMMddhhmmsszzz"), QString()); 0132 formatStrings << qMakePair(QLatin1String("yyyyMMddhhmmss"), QString()); 0133 formatStrings << qMakePair(QLatin1String("ddMMyyyyhhmmss"), QLatin1String("MMddyyyyhhmmss")); 0134 formatStrings << qMakePair(QLatin1String("ddMMyyyyhhmm"), QLatin1String("MMddyyyyhhmm")); 0135 formatStrings << qMakePair(QLatin1String("ddMMyyhhmm"), QString()); 0136 formatStrings << qMakePair(QLatin1String("yyyyMMdd"), QString()); 0137 formatStrings << qMakePair(QLatin1String("ddMMyyyy"), QLatin1String("MMddyyyy")); 0138 formatStrings << qMakePair(QLatin1String("ddMMyyyy"), QLatin1String("MMddyyyy")); 0139 formatStrings << qMakePair(QLatin1String("ddMM yy"), QString()); 0140 0141 QDateTime dateTime; 0142 0143 for (int index = 0 ; index < regExpStrings.count() ; ++index) 0144 { 0145 QRegularExpression dateRegExp(QRegularExpression::anchoredPattern(regExpStrings.at(index))); 0146 QRegularExpressionMatch match = dateRegExp.match(dateStr); 0147 0148 if (match.hasMatch()) 0149 { 0150 QString dateString = match.captured(2); 0151 QString format = formatStrings.at(index).first; 0152 QString secondFormat = formatStrings.at(index).second; 0153 0154 if (format.contains(QLatin1String("hhmm"))) 0155 { 0156 dateString.append(match.captured(4)); 0157 } 0158 0159 dateString.remove(QLatin1Char(' ')); 0160 dateString.remove(QLatin1Char('-')); 0161 dateString.remove(QLatin1Char('_')); 0162 dateString.remove(QLatin1Char(':')); 0163 dateString.remove(QLatin1Char('.')); 0164 dateString.remove(QLatin1Char('/')); 0165 dateString.remove(QLatin1Char('T')); 0166 dateString.remove(QLatin1Char('h')); 0167 dateString.remove(QLatin1Char('H')); 0168 0169 dateTime = QDateTime::fromString(dateString, format); 0170 dateTime.setTimeSpec(Qt::UTC); 0171 0172 if (!dateTime.isValid() && !secondFormat.isEmpty()) 0173 { 0174 format = secondFormat; 0175 dateTime = QDateTime::fromString(dateString, format); 0176 dateTime.setTimeSpec(Qt::UTC); 0177 } 0178 0179 if (dateTime.isValid() && (format.count(QLatin1Char('y')) == 2)) 0180 { 0181 if (dateTime.date().year() < 1970) 0182 { 0183 dateTime.setDate(dateTime.date().addYears(100)); 0184 } 0185 } 0186 0187 if (!dateTime.isValid() || 0188 (dateTime.date().year() < 1800) || 0189 (dateTime.date().year() > 2200)) 0190 { 0191 dateTime = QDateTime(); 0192 } 0193 else 0194 { 0195 break; 0196 } 0197 } 0198 } 0199 0200 return dateTime; 0201 } 0202 0203 QMap<QString, bool> TimeAdjustContainer::getDateTimeTagsMap() const 0204 { 0205 QMap<QString, bool> tagsMap; 0206 0207 tagsMap.insert(QLatin1String("Exif.Image.DateTime"), updEXIFModDate); 0208 tagsMap.insert(QLatin1String("Exif.Photo.DateTimeOriginal"), updEXIFOriDate); 0209 tagsMap.insert(QLatin1String("Exif.Photo.DateTimeDigitized"), updEXIFDigDate); 0210 tagsMap.insert(QLatin1String("Exif.Image.PreviewDateTime"), updEXIFThmDate); 0211 0212 tagsMap.insert(QLatin1String("Iptc.Application2.DateCreated"), updIPTCDate); 0213 tagsMap.insert(QLatin1String("Iptc.Application2.TimeCreated"), updIPTCDate); 0214 0215 tagsMap.insert(QLatin1String("Xmp.exif.DateTimeOriginal"), updXMPDate); 0216 tagsMap.insert(QLatin1String("Xmp.photoshop.DateCreated"), updXMPDate); 0217 tagsMap.insert(QLatin1String("Xmp.xmp.MetadataDate"), updXMPDate); 0218 tagsMap.insert(QLatin1String("Xmp.xmp.CreateDate"), updXMPDate); 0219 tagsMap.insert(QLatin1String("Xmp.xmp.ModifyDate"), updXMPDate); 0220 tagsMap.insert(QLatin1String("Xmp.tiff.DateTime"), updXMPDate); 0221 0222 tagsMap.insert(QLatin1String("Xmp.video.DateTimeOriginal"), updXMPVideo); 0223 tagsMap.insert(QLatin1String("Xmp.video.DateTimeDigitized"), updXMPVideo); 0224 tagsMap.insert(QLatin1String("Xmp.video.ModificationDate"), updXMPVideo); 0225 tagsMap.insert(QLatin1String("Xmp.video.DateUTC"), updXMPVideo); 0226 0227 tagsMap.insert(QLatin1String("Xmp.xmpDM.shotDate"), updXMPVideo); 0228 0229 return tagsMap; 0230 } 0231 // ------------------------------------------------------------------- 0232 0233 DeltaTime::DeltaTime() 0234 : deltaNegative(false), 0235 deltaDays (0), 0236 deltaHours (0), 0237 deltaMinutes (0), 0238 deltaSeconds (0) 0239 { 0240 } 0241 0242 DeltaTime::~DeltaTime() 0243 { 0244 } 0245 0246 bool DeltaTime::isNull() const 0247 { 0248 return ( 0249 (deltaDays == 0) && 0250 (deltaHours == 0) && 0251 (deltaMinutes == 0) && 0252 (deltaSeconds == 0) 0253 ); 0254 } 0255 0256 } // namespace Digikam