File indexing completed on 2024-06-23 05:18:31

0001 /*
0002    SPDX-FileCopyrightText: 2012-2024 Laurent Montel <montel@kde.org>
0003 
0004    SPDX-License-Identifier: GPL-2.0-or-later
0005 */
0006 
0007 #include "imagescalingwidget.h"
0008 #include "settings/messagecomposersettings.h"
0009 #include "ui_imagescalingwidget.h"
0010 #include <KLineEditEventHandler>
0011 #include <KLocalizedString>
0012 #include <KMessageBox>
0013 
0014 #include <QButtonGroup>
0015 #include <QComboBox>
0016 #include <QImageWriter>
0017 #include <QList>
0018 #include <QWhatsThis>
0019 
0020 using namespace MessageComposer;
0021 class MessageComposer::ImageScalingWidgetPrivate
0022 {
0023 public:
0024     ImageScalingWidgetPrivate()
0025         : ui(new Ui::ImageScalingWidget)
0026     {
0027     }
0028 
0029     ~ImageScalingWidgetPrivate()
0030     {
0031         delete ui;
0032     }
0033 
0034     Ui::ImageScalingWidget *const ui;
0035     QButtonGroup *mSourceFilenameFilterGroup = nullptr;
0036     QButtonGroup *mRecipientFilterGroup = nullptr;
0037     bool mWasChanged = false;
0038 };
0039 
0040 ImageScalingWidget::ImageScalingWidget(QWidget *parent)
0041     : QWidget(parent)
0042     , d(new MessageComposer::ImageScalingWidgetPrivate)
0043 {
0044     d->ui->setupUi(this);
0045     initComboBox(d->ui->CBMaximumWidth);
0046     initComboBox(d->ui->CBMaximumHeight);
0047     initComboBox(d->ui->CBMinimumWidth);
0048     initComboBox(d->ui->CBMinimumHeight);
0049 
0050     initWriteImageFormat();
0051     KLineEditEventHandler::catchReturnKey(d->ui->pattern);
0052     KLineEditEventHandler::catchReturnKey(d->ui->renameResizedImagePattern);
0053     KLineEditEventHandler::catchReturnKey(d->ui->resizeEmailsPattern);
0054     KLineEditEventHandler::catchReturnKey(d->ui->doNotResizePattern);
0055 
0056     connect(d->ui->enabledAutoResize, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0057     connect(d->ui->KeepImageRatio, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0058     connect(d->ui->AskBeforeResizing, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0059     connect(d->ui->EnlargeImageToMinimum, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0060     connect(d->ui->ReduceImageToMaximum, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0061     connect(d->ui->customMaximumWidth, &QSpinBox::valueChanged, this, &ImageScalingWidget::changed);
0062     connect(d->ui->customMaximumHeight, &QSpinBox::valueChanged, this, &ImageScalingWidget::changed);
0063     connect(d->ui->customMinimumWidth, &QSpinBox::valueChanged, this, &ImageScalingWidget::changed);
0064     connect(d->ui->customMinimumHeight, &QSpinBox::valueChanged, this, &ImageScalingWidget::changed);
0065     connect(d->ui->skipImageSizeLower, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0066     connect(d->ui->imageSize, &QSpinBox::valueChanged, this, &ImageScalingWidget::changed);
0067     connect(d->ui->pattern, &QLineEdit::textChanged, this, &ImageScalingWidget::changed);
0068     connect(d->ui->CBMaximumWidth, &QComboBox::currentIndexChanged, this, &ImageScalingWidget::slotComboboxChanged);
0069     connect(d->ui->CBMaximumHeight, &QComboBox::currentIndexChanged, this, &ImageScalingWidget::slotComboboxChanged);
0070     connect(d->ui->CBMinimumWidth, &QComboBox::currentIndexChanged, this, &ImageScalingWidget::slotComboboxChanged);
0071     connect(d->ui->CBMinimumHeight, &QComboBox::currentIndexChanged, this, &ImageScalingWidget::slotComboboxChanged);
0072     connect(d->ui->WriteToImageFormat, &QComboBox::activated, this, &ImageScalingWidget::changed);
0073     connect(d->ui->renameResizedImage, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0074     connect(d->ui->renameResizedImage, &QCheckBox::clicked, d->ui->renameResizedImagePattern, &QLineEdit::setEnabled);
0075     connect(d->ui->renameResizedImagePattern, &QLineEdit::textChanged, this, &ImageScalingWidget::changed);
0076 
0077     connect(d->ui->resizeEmailsPattern, &QLineEdit::textChanged, this, &ImageScalingWidget::changed);
0078     connect(d->ui->doNotResizePattern, &QLineEdit::textChanged, this, &ImageScalingWidget::changed);
0079     connect(d->ui->resizeImageWithFormatsType, &MessageComposer::ImageScalingSelectFormat::textChanged, this, &ImageScalingWidget::changed);
0080     connect(d->ui->resizeImageWithFormats, &QCheckBox::clicked, this, &ImageScalingWidget::changed);
0081     connect(d->ui->resizeImageWithFormats, &QCheckBox::clicked, d->ui->resizeImageWithFormatsType, &MessageComposer::ImageScalingSelectFormat::setEnabled);
0082     d->ui->resizeImageWithFormatsType->setEnabled(false);
0083 
0084     d->ui->pattern->setEnabled(false);
0085     d->mSourceFilenameFilterGroup = new QButtonGroup(d->ui->filterSourceGroupBox);
0086     connect(d->mSourceFilenameFilterGroup, &QButtonGroup::buttonClicked, this, &ImageScalingWidget::slotSourceFilterAbstractButtonClicked);
0087     d->mSourceFilenameFilterGroup->addButton(d->ui->notFilterFilename, MessageComposer::MessageComposerSettings::EnumFilterSourceType::NoFilter);
0088     d->mSourceFilenameFilterGroup->addButton(d->ui->includeFilesWithPattern,
0089                                              MessageComposer::MessageComposerSettings::EnumFilterSourceType::IncludeFilesWithPattern);
0090     d->mSourceFilenameFilterGroup->addButton(d->ui->excludeFilesWithPattern,
0091                                              MessageComposer::MessageComposerSettings::EnumFilterSourceType::ExcludeFilesWithPattern);
0092 
0093     d->mRecipientFilterGroup = new QButtonGroup(d->ui->tab_4);
0094     connect(d->mRecipientFilterGroup, &QButtonGroup::buttonClicked, this, &ImageScalingWidget::slotRecipientFilterAbstractClicked);
0095     d->ui->doNotResizePattern->setEnabled(false);
0096     d->ui->resizeEmailsPattern->setEnabled(false);
0097     d->mRecipientFilterGroup->addButton(d->ui->doNotFilterRecipients, MessageComposer::MessageComposerSettings::EnumFilterRecipientType::NoFilter);
0098     d->mRecipientFilterGroup->addButton(d->ui->resizeEachEmails,
0099                                         MessageComposer::MessageComposerSettings::EnumFilterRecipientType::ResizeEachEmailsContainsPattern);
0100     d->mRecipientFilterGroup->addButton(d->ui->resizeOneEmails,
0101                                         MessageComposer::MessageComposerSettings::EnumFilterRecipientType::ResizeOneEmailContainsPattern);
0102     d->mRecipientFilterGroup->addButton(d->ui->doNotResizeEachEmails,
0103                                         MessageComposer::MessageComposerSettings::EnumFilterRecipientType::DontResizeEachEmailsContainsPattern);
0104     d->mRecipientFilterGroup->addButton(d->ui->doNotResizeOneEmails,
0105                                         MessageComposer::MessageComposerSettings::EnumFilterRecipientType::DontResizeOneEmailContainsPattern);
0106 
0107     d->ui->help->setText(i18n("<a href=\"whatsthis\">How does this work?</a>"));
0108     connect(d->ui->help, &QLabel::linkActivated, this, &ImageScalingWidget::slotHelpLinkClicked);
0109     d->ui->help->setContextMenuPolicy(Qt::NoContextMenu);
0110 }
0111 
0112 ImageScalingWidget::~ImageScalingWidget() = default;
0113 
0114 void ImageScalingWidget::slotHelpLinkClicked(const QString &)
0115 {
0116     const QString help = i18n(
0117         "<qt>"
0118         "<p>Here you can define image filename. "
0119         "You can use:</p>"
0120         "<ul>"
0121         "<li>%t set current time</li>"
0122         "<li>%d set current date</li>"
0123         "<li>%n original filename</li>"
0124         "<li>%e original extension</li>"
0125         "<li>%x new extension</li>"
0126         "</ul>"
0127         "</qt>");
0128 
0129     QWhatsThis::showText(QCursor::pos(), help);
0130 }
0131 
0132 void ImageScalingWidget::slotSourceFilterAbstractButtonClicked(QAbstractButton *button)
0133 {
0134     if (button) {
0135         const int buttonId = d->mRecipientFilterGroup->id(button);
0136         slotSourceFilterClicked(buttonId);
0137     }
0138 }
0139 
0140 void ImageScalingWidget::slotSourceFilterClicked(int button)
0141 {
0142     d->ui->pattern->setEnabled(button != 0);
0143     Q_EMIT changed();
0144 }
0145 
0146 void ImageScalingWidget::slotRecipientFilterClicked(int button)
0147 {
0148     d->ui->resizeEmailsPattern->setEnabled((button == MessageComposer::MessageComposerSettings::EnumFilterRecipientType::ResizeEachEmailsContainsPattern)
0149                                            || (button == MessageComposer::MessageComposerSettings::EnumFilterRecipientType::ResizeOneEmailContainsPattern));
0150     d->ui->doNotResizePattern->setEnabled((button == MessageComposer::MessageComposerSettings::EnumFilterRecipientType::DontResizeEachEmailsContainsPattern)
0151                                           || (button == MessageComposer::MessageComposerSettings::EnumFilterRecipientType::DontResizeOneEmailContainsPattern));
0152     Q_EMIT changed();
0153 }
0154 
0155 void ImageScalingWidget::slotRecipientFilterAbstractClicked(QAbstractButton *button)
0156 {
0157     if (button) {
0158         const int buttonId = d->mRecipientFilterGroup->id(button);
0159         slotRecipientFilterClicked(buttonId);
0160     }
0161 }
0162 
0163 void ImageScalingWidget::slotComboboxChanged(int index)
0164 {
0165     auto combo = qobject_cast<QComboBox *>(sender());
0166     if (combo) {
0167         const bool isCustom = combo->itemData(index) == -1;
0168         if (combo == d->ui->CBMaximumWidth) {
0169             d->ui->customMaximumWidth->setEnabled(isCustom);
0170         } else if (combo == d->ui->CBMaximumHeight) {
0171             d->ui->customMaximumHeight->setEnabled(isCustom);
0172         } else if (combo == d->ui->CBMinimumWidth) {
0173             d->ui->customMinimumWidth->setEnabled(isCustom);
0174         } else if (combo == d->ui->CBMinimumHeight) {
0175             d->ui->customMinimumHeight->setEnabled(isCustom);
0176         }
0177         Q_EMIT changed();
0178     }
0179 }
0180 
0181 void ImageScalingWidget::initComboBox(QComboBox *combo)
0182 {
0183     const QList<int> size = {240, 320, 512, 640, 800, 1024, 1600, 2048};
0184     for (int val : size) {
0185         combo->addItem(QStringLiteral("%1 px").arg(QString::number(val)), val);
0186     }
0187     combo->addItem(i18n("Custom"), -1);
0188 }
0189 
0190 void ImageScalingWidget::initWriteImageFormat()
0191 {
0192     /* Too many format :)
0193     QList<QByteArray> listWriteFormat = QImageWriter::supportedImageFormats();
0194     Q_FOREACH(const QByteArray& format, listWriteFormat) {
0195         d->ui->WriteToImageFormat->addItem(QString::fromLatin1(format));
0196     }
0197     */
0198     // known by several mailer.
0199     d->ui->WriteToImageFormat->addItem(QStringLiteral("JPG"));
0200     d->ui->WriteToImageFormat->addItem(QStringLiteral("PNG"));
0201 }
0202 
0203 void ImageScalingWidget::updateSettings()
0204 {
0205     d->ui->enabledAutoResize->setChecked(MessageComposer::MessageComposerSettings::self()->autoResizeImageEnabled());
0206     d->ui->KeepImageRatio->setChecked(MessageComposer::MessageComposerSettings::self()->keepImageRatio());
0207     d->ui->AskBeforeResizing->setChecked(MessageComposer::MessageComposerSettings::self()->askBeforeResizing());
0208     d->ui->EnlargeImageToMinimum->setChecked(MessageComposer::MessageComposerSettings::self()->enlargeImageToMinimum());
0209     d->ui->ReduceImageToMaximum->setChecked(MessageComposer::MessageComposerSettings::self()->reduceImageToMaximum());
0210     d->ui->skipImageSizeLower->setChecked(MessageComposer::MessageComposerSettings::self()->skipImageLowerSizeEnabled());
0211     d->ui->imageSize->setValue(MessageComposer::MessageComposerSettings::self()->skipImageLowerSize());
0212 
0213     d->ui->customMaximumWidth->setValue(MessageComposer::MessageComposerSettings::self()->customMaximumWidth());
0214     d->ui->customMaximumHeight->setValue(MessageComposer::MessageComposerSettings::self()->customMaximumHeight());
0215     d->ui->customMinimumWidth->setValue(MessageComposer::MessageComposerSettings::self()->customMinimumWidth());
0216     d->ui->customMinimumHeight->setValue(MessageComposer::MessageComposerSettings::self()->customMinimumHeight());
0217 
0218     int index = qMax(0, d->ui->CBMaximumWidth->findData(MessageComposer::MessageComposerSettings::self()->maximumWidth()));
0219     d->ui->CBMaximumWidth->setCurrentIndex(index);
0220     d->ui->customMaximumWidth->setEnabled(d->ui->CBMaximumWidth->itemData(index) == -1);
0221 
0222     index = qMax(0, d->ui->CBMaximumHeight->findData(MessageComposer::MessageComposerSettings::self()->maximumHeight()));
0223     d->ui->CBMaximumHeight->setCurrentIndex(index);
0224     d->ui->customMaximumHeight->setEnabled(d->ui->CBMaximumHeight->itemData(index) == -1);
0225 
0226     index = qMax(0, d->ui->CBMinimumWidth->findData(MessageComposer::MessageComposerSettings::self()->minimumWidth()));
0227     d->ui->CBMinimumWidth->setCurrentIndex(index);
0228     d->ui->customMinimumWidth->setEnabled(d->ui->CBMinimumWidth->itemData(index) == -1);
0229 
0230     index = qMax(0, d->ui->CBMinimumHeight->findData(MessageComposer::MessageComposerSettings::self()->minimumHeight()));
0231     d->ui->CBMinimumHeight->setCurrentIndex(index);
0232     d->ui->customMinimumHeight->setEnabled(d->ui->CBMinimumHeight->itemData(index) == -1);
0233 
0234     index = d->ui->WriteToImageFormat->findData(MessageComposer::MessageComposerSettings::self()->writeFormat());
0235     if (index == -1) {
0236         d->ui->WriteToImageFormat->setCurrentIndex(0);
0237     } else {
0238         d->ui->WriteToImageFormat->setCurrentIndex(index);
0239     }
0240     d->ui->pattern->setText(MessageComposer::MessageComposerSettings::self()->filterSourcePattern());
0241 
0242     d->ui->renameResizedImage->setChecked(MessageComposer::MessageComposerSettings::self()->renameResizedImages());
0243 
0244     d->ui->renameResizedImagePattern->setText(MessageComposer::MessageComposerSettings::self()->renameResizedImagesPattern());
0245     d->ui->renameResizedImagePattern->setEnabled(d->ui->renameResizedImage->isChecked());
0246 
0247     d->ui->doNotResizePattern->setText(MessageComposer::MessageComposerSettings::self()->doNotResizeEmailsPattern());
0248     d->ui->resizeEmailsPattern->setText(MessageComposer::MessageComposerSettings::self()->resizeEmailsPattern());
0249 
0250     d->ui->resizeImageWithFormats->setChecked(MessageComposer::MessageComposerSettings::self()->resizeImagesWithFormats());
0251     d->ui->resizeImageWithFormatsType->setFormat(MessageComposer::MessageComposerSettings::self()->resizeImagesWithFormatsType());
0252     d->ui->resizeImageWithFormatsType->setEnabled(d->ui->resizeImageWithFormats->isChecked());
0253 
0254     updateFilterSourceTypeSettings();
0255     updateEmailsFilterTypeSettings();
0256 }
0257 
0258 void ImageScalingWidget::loadConfig()
0259 {
0260     updateSettings();
0261     d->mWasChanged = false;
0262 }
0263 
0264 void ImageScalingWidget::updateFilterSourceTypeSettings()
0265 {
0266     switch (MessageComposer::MessageComposerSettings::self()->filterSourceType()) {
0267     case MessageComposer::MessageComposerSettings::EnumFilterSourceType::NoFilter:
0268         d->ui->notFilterFilename->setChecked(true);
0269         d->ui->pattern->setEnabled(false);
0270         break;
0271     case MessageComposer::MessageComposerSettings::EnumFilterSourceType::IncludeFilesWithPattern:
0272         d->ui->includeFilesWithPattern->setChecked(true);
0273         d->ui->pattern->setEnabled(true);
0274         break;
0275     case MessageComposer::MessageComposerSettings::EnumFilterSourceType::ExcludeFilesWithPattern:
0276         d->ui->excludeFilesWithPattern->setChecked(true);
0277         d->ui->pattern->setEnabled(true);
0278         break;
0279     }
0280 }
0281 
0282 void ImageScalingWidget::updateEmailsFilterTypeSettings()
0283 {
0284     d->ui->doNotResizePattern->setEnabled(false);
0285     d->ui->resizeEmailsPattern->setEnabled(false);
0286 
0287     switch (MessageComposer::MessageComposerSettings::self()->filterRecipientType()) {
0288     case MessageComposer::MessageComposerSettings::EnumFilterRecipientType::NoFilter:
0289         d->ui->doNotFilterRecipients->setChecked(true);
0290         break;
0291     case MessageComposer::MessageComposerSettings::EnumFilterRecipientType::ResizeEachEmailsContainsPattern:
0292         d->ui->resizeEachEmails->setChecked(true);
0293         d->ui->resizeEmailsPattern->setEnabled(true);
0294         break;
0295     case MessageComposer::MessageComposerSettings::EnumFilterRecipientType::ResizeOneEmailContainsPattern:
0296         d->ui->resizeOneEmails->setChecked(true);
0297         d->ui->resizeEmailsPattern->setEnabled(true);
0298         break;
0299     case MessageComposer::MessageComposerSettings::EnumFilterRecipientType::DontResizeEachEmailsContainsPattern:
0300         d->ui->doNotResizeEachEmails->setChecked(true);
0301         d->ui->doNotResizePattern->setEnabled(true);
0302         break;
0303     case MessageComposer::MessageComposerSettings::EnumFilterRecipientType::DontResizeOneEmailContainsPattern:
0304         d->ui->doNotResizeOneEmails->setChecked(true);
0305         d->ui->doNotResizePattern->setEnabled(false);
0306         break;
0307     }
0308 }
0309 
0310 void ImageScalingWidget::writeConfig()
0311 {
0312     if (d->ui->EnlargeImageToMinimum->isChecked() && d->ui->ReduceImageToMaximum->isChecked()) {
0313         if ((d->ui->customMinimumWidth->value() >= d->ui->customMaximumWidth->value())
0314             || (d->ui->customMinimumHeight->value() >= d->ui->customMaximumHeight->value())) {
0315             KMessageBox::error(this, i18n("Please verify minimum and maximum values."), i18nc("@title:window", "Error in minimum Maximum value"));
0316             return;
0317         }
0318     }
0319     MessageComposer::MessageComposerSettings::self()->setAutoResizeImageEnabled(d->ui->enabledAutoResize->isChecked());
0320     MessageComposer::MessageComposerSettings::self()->setKeepImageRatio(d->ui->KeepImageRatio->isChecked());
0321     MessageComposer::MessageComposerSettings::self()->setAskBeforeResizing(d->ui->AskBeforeResizing->isChecked());
0322     MessageComposer::MessageComposerSettings::self()->setEnlargeImageToMinimum(d->ui->EnlargeImageToMinimum->isChecked());
0323     MessageComposer::MessageComposerSettings::self()->setReduceImageToMaximum(d->ui->ReduceImageToMaximum->isChecked());
0324 
0325     MessageComposer::MessageComposerSettings::self()->setCustomMaximumWidth(d->ui->customMaximumWidth->value());
0326     MessageComposer::MessageComposerSettings::self()->setCustomMaximumHeight(d->ui->customMaximumHeight->value());
0327     MessageComposer::MessageComposerSettings::self()->setCustomMinimumWidth(d->ui->customMinimumWidth->value());
0328     MessageComposer::MessageComposerSettings::self()->setCustomMinimumHeight(d->ui->customMinimumHeight->value());
0329 
0330     MessageComposer::MessageComposerSettings::self()->setMaximumWidth(d->ui->CBMaximumWidth->itemData(d->ui->CBMaximumWidth->currentIndex()).toInt());
0331     MessageComposer::MessageComposerSettings::self()->setMaximumHeight(d->ui->CBMaximumHeight->itemData(d->ui->CBMaximumHeight->currentIndex()).toInt());
0332     MessageComposer::MessageComposerSettings::self()->setMinimumWidth(d->ui->CBMinimumWidth->itemData(d->ui->CBMinimumWidth->currentIndex()).toInt());
0333     MessageComposer::MessageComposerSettings::self()->setMinimumHeight(d->ui->CBMinimumHeight->itemData(d->ui->CBMinimumHeight->currentIndex()).toInt());
0334 
0335     MessageComposer::MessageComposerSettings::self()->setWriteFormat(d->ui->WriteToImageFormat->currentText());
0336     MessageComposer::MessageComposerSettings::self()->setSkipImageLowerSizeEnabled(d->ui->skipImageSizeLower->isChecked());
0337     MessageComposer::MessageComposerSettings::self()->setSkipImageLowerSize(d->ui->imageSize->value());
0338 
0339     MessageComposer::MessageComposerSettings::self()->setFilterSourcePattern(d->ui->pattern->text());
0340 
0341     MessageComposer::MessageComposerSettings::self()->setFilterSourceType(d->mSourceFilenameFilterGroup->checkedId());
0342 
0343     MessageComposer::MessageComposerSettings::self()->setRenameResizedImages(d->ui->renameResizedImage->isChecked());
0344 
0345     MessageComposer::MessageComposerSettings::self()->setRenameResizedImagesPattern(d->ui->renameResizedImagePattern->text());
0346 
0347     MessageComposer::MessageComposerSettings::self()->setDoNotResizeEmailsPattern(d->ui->doNotResizePattern->text());
0348     MessageComposer::MessageComposerSettings::self()->setResizeEmailsPattern(d->ui->resizeEmailsPattern->text());
0349     MessageComposer::MessageComposerSettings::self()->setFilterRecipientType(d->mRecipientFilterGroup->checkedId());
0350 
0351     MessageComposer::MessageComposerSettings::self()->setResizeImagesWithFormats(d->ui->resizeImageWithFormats->isChecked());
0352     MessageComposer::MessageComposerSettings::self()->setResizeImagesWithFormatsType(d->ui->resizeImageWithFormatsType->format());
0353     d->mWasChanged = false;
0354 }
0355 
0356 void ImageScalingWidget::resetToDefault()
0357 {
0358     const bool bUseDefaults = MessageComposer::MessageComposerSettings::self()->useDefaults(true);
0359     updateSettings();
0360     MessageComposer::MessageComposerSettings::self()->useDefaults(bUseDefaults);
0361 }
0362 
0363 #include "moc_imagescalingwidget.cpp"