File indexing completed on 2024-05-05 04:22:02
0001 // SPDX-FileCopyrightText: 2003-2020 Jesper K. Pedersen <blackie@kde.org> 0002 // SPDX-FileCopyrightText: 2021 Johannes Zarl-Zierl <johannes@zarl-zierl.at> 0003 // 0004 // SPDX-License-Identifier: GPL-2.0-or-later 0005 0006 #include "MD5CheckPage.h" 0007 0008 #include <DB/ImageDB.h> 0009 #include <DB/MD5Map.h> 0010 0011 #include <KLocalizedString> 0012 #include <QButtonGroup> 0013 #include <QFrame> 0014 #include <QLabel> 0015 #include <QRadioButton> 0016 #include <QVBoxLayout> 0017 0018 ImportExport::ClashInfo::ClashInfo(const QStringList &categories) 0019 : label(false) 0020 , description(false) 0021 , orientation(false) 0022 , date(false) 0023 { 0024 for (const QString &category : categories) 0025 this->categories[category] = false; 0026 } 0027 0028 bool ImportExport::MD5CheckPage::pageNeeded(const ImportSettings &settings) 0029 { 0030 if (countOfMD5Matches(settings) != 0 && clashes(settings).anyClashes()) 0031 return true; 0032 0033 return false; 0034 } 0035 0036 ImportExport::MD5CheckPage::MD5CheckPage(const ImportSettings &settings) 0037 { 0038 QVBoxLayout *vlay = new QVBoxLayout(this); 0039 0040 const QString txt = i18np("One image from the import file, has the same MD5 sum as an image in the Database, how should that be resolved?", 0041 "%1 images from the import file, have the same MD5 sum as images in the Database, how should that be resolved?", 0042 countOfMD5Matches(settings)); 0043 QLabel *label = new QLabel(txt); 0044 label->setWordWrap(true); 0045 0046 vlay->addWidget(label); 0047 0048 QGridLayout *grid = new QGridLayout; 0049 grid->setHorizontalSpacing(0); 0050 vlay->addLayout(grid); 0051 0052 int row = -1; 0053 0054 // Titles 0055 label = new QLabel(i18n("Use data from\nImport File")); 0056 grid->addWidget(label, ++row, 1); 0057 0058 label = new QLabel(i18n("Use data from\nDatabase")); 0059 grid->addWidget(label, row, 2); 0060 0061 label = new QLabel(i18n("Merge data")); 0062 grid->addWidget(label, row, 3); 0063 0064 ClashInfo clashes = this->clashes(settings); 0065 createRow(grid, row, QString::fromLatin1("*Label*"), i18n("Label"), clashes.label, false); 0066 createRow(grid, row, QString::fromLatin1("*Description*"), i18n("Description"), clashes.description, true); 0067 createRow(grid, row, QString::fromLatin1("*Orientation*"), i18n("Orientation"), clashes.orientation, false); 0068 createRow(grid, row, QString::fromLatin1("*Date*"), i18n("Date and Time"), clashes.date, false); 0069 for (QMap<QString, bool>::const_iterator it = clashes.categories.constBegin(); it != clashes.categories.constEnd(); ++it) { 0070 createRow(grid, row, it.key(), it.key(), *it, true); 0071 } 0072 0073 vlay->addStretch(1); 0074 } 0075 0076 /** 0077 * Return the number of images in the import set which has the same MD5 sum as those from the DB. 0078 */ 0079 int ImportExport::MD5CheckPage::countOfMD5Matches(const ImportSettings &settings) 0080 { 0081 int count = 0; 0082 DB::ImageInfoList list = settings.selectedImages(); 0083 for (DB::ImageInfoPtr info : list) { 0084 if (DB::ImageDB::instance()->md5Map()->contains(info->MD5Sum())) 0085 ++count; 0086 } 0087 return count; 0088 } 0089 0090 ImportExport::ClashInfo ImportExport::MD5CheckPage::clashes(const ImportSettings &settings) 0091 { 0092 QStringList myCategories; 0093 const auto categoryMatchSettings = settings.categoryMatchSetting(); 0094 for (const CategoryMatchSetting &matcher : categoryMatchSettings) { 0095 myCategories.append(matcher.DBCategoryName()); 0096 } 0097 0098 ClashInfo res(myCategories); 0099 const DB::ImageInfoList list = settings.selectedImages(); 0100 for (const DB::ImageInfoPtr &info : list) { 0101 if (!DB::ImageDB::instance()->md5Map()->contains(info->MD5Sum())) 0102 continue; 0103 0104 const DB::FileName name = DB::ImageDB::instance()->md5Map()->lookup(info->MD5Sum()); 0105 const DB::ImageInfoPtr other = DB::ImageDB::instance()->info(name); 0106 if (other->isNull()) 0107 continue; 0108 if (info->label() != other->label()) 0109 res.label = true; 0110 if (info->description() != other->description()) 0111 res.description = true; 0112 0113 if (info->angle() != other->angle()) 0114 res.orientation = true; 0115 0116 if (info->date() != other->date()) 0117 res.date = true; 0118 0119 const auto categoryMatchSettings = settings.categoryMatchSetting(); 0120 for (const CategoryMatchSetting &matcher : categoryMatchSettings) { 0121 const QString XMLFileCategory = matcher.XMLCategoryName(); 0122 const QString DBCategory = matcher.DBCategoryName(); 0123 if (mapCategoriesToDB(matcher, info->itemsOfCategory(XMLFileCategory)) != other->itemsOfCategory(DBCategory)) 0124 res.categories[DBCategory] = true; 0125 } 0126 } 0127 return res; 0128 } 0129 0130 bool ImportExport::ClashInfo::anyClashes() 0131 { 0132 if (label || description || orientation || date) 0133 return true; 0134 0135 for (QMap<QString, bool>::ConstIterator categoryIt = categories.constBegin(); categoryIt != categories.constEnd(); ++categoryIt) { 0136 if (categoryIt.value()) 0137 return true; 0138 } 0139 0140 return false; 0141 } 0142 0143 void ImportExport::MD5CheckPage::createRow(QGridLayout *layout, int &row, const QString &name, const QString &title, bool anyClashes, bool allowMerge) 0144 { 0145 if (row % 3 == 0) { 0146 QFrame *line = new QFrame; 0147 line->setFrameShape(QFrame::HLine); 0148 layout->addWidget(line, ++row, 0, 1, 4); 0149 } 0150 0151 QLabel *label = new QLabel(title); 0152 label->setEnabled(anyClashes); 0153 layout->addWidget(label, ++row, 0); 0154 0155 QButtonGroup *group = new QButtonGroup(this); 0156 m_groups[name] = group; 0157 0158 for (int i = 1; i < 4; ++i) { 0159 if (i == 3 && !allowMerge) 0160 continue; 0161 0162 QRadioButton *rb = new QRadioButton; 0163 layout->addWidget(rb, row, i); 0164 group->addButton(rb, i); 0165 rb->setEnabled(anyClashes); 0166 if (i == 1) 0167 rb->setChecked(true); 0168 } 0169 } 0170 0171 Utilities::StringSet ImportExport::MD5CheckPage::mapCategoriesToDB(const CategoryMatchSetting &matcher, const Utilities::StringSet &items) 0172 { 0173 Utilities::StringSet res; 0174 0175 for (const QString &item : items) { 0176 if (matcher.XMLtoDB().contains(item)) 0177 res.insert(matcher.XMLtoDB()[item]); 0178 } 0179 return res; 0180 } 0181 0182 QMap<QString, ImportExport::ImportSettings::ImportAction> ImportExport::MD5CheckPage::settings() 0183 { 0184 QMap<QString, ImportSettings::ImportAction> res; 0185 for (QMap<QString, QButtonGroup *>::iterator it = m_groups.begin(); it != m_groups.end(); ++it) { 0186 res.insert(it.key(), static_cast<ImportSettings::ImportAction>(it.value()->checkedId())); 0187 } 0188 return res; 0189 } 0190 0191 // vi:expandtab:tabstop=4 shiftwidth=4: