File indexing completed on 2024-06-02 05:43:39
0001 /* ColorEdit widget for KDE Display color scheme setup module 0002 SPDX-FileCopyrightText: 2016 Olivier Churlaud <olivier@churlaud.com> 0003 0004 SPDX-License-Identifier: GPL-2.0-or-later 0005 */ 0006 0007 #include "scmeditordialog.h" 0008 #include "scmeditorcolors.h" 0009 #include "scmeditoreffects.h" 0010 #include "scmeditoroptions.h" 0011 0012 #include <QDebug> 0013 #include <QDir> 0014 #include <QInputDialog> 0015 #include <QLineEdit> 0016 #include <QUrl> 0017 0018 #include <KConfigGroup> 0019 #include <KMessageBox> 0020 #include <KStandardGuiItem> 0021 #include <KWindowSystem> 0022 0023 using namespace Qt::StringLiterals; 0024 0025 SchemeEditorDialog::SchemeEditorDialog(KSharedConfigPtr config, QWidget *parent) 0026 : QDialog(parent) 0027 , m_config(config) 0028 { 0029 init(); 0030 } 0031 0032 SchemeEditorDialog::SchemeEditorDialog(const QString &path, QWidget *parent) 0033 : QDialog(parent) 0034 , m_filePath(path) 0035 , m_config(KSharedConfig::openConfig(path, KSharedConfig::SimpleConfig)) 0036 { 0037 m_schemeName = KConfigGroup(m_config, u"General"_s).readEntry("Name"); 0038 this->setWindowTitle(m_schemeName); 0039 init(); 0040 } 0041 0042 bool SchemeEditorDialog::showApplyOverwriteButton() const 0043 { 0044 return m_showApplyOverwriteButton; 0045 } 0046 0047 void SchemeEditorDialog::setShowApplyOverwriteButton(bool show) 0048 { 0049 m_showApplyOverwriteButton = show; 0050 0051 buttonBox->button(QDialogButtonBox::Apply)->setVisible(show); 0052 } 0053 0054 void SchemeEditorDialog::init() 0055 { 0056 setupUi(this); 0057 0058 m_optionTab = new SchemeEditorOptions(m_config); 0059 m_colorTab = new SchemeEditorColors(m_config); 0060 m_disabledTab = new SchemeEditorEffects(m_config, QPalette::Disabled); 0061 m_inactiveTab = new SchemeEditorEffects(m_config, QPalette::Inactive); 0062 tabWidget->addTab(m_optionTab, i18n("Options")); 0063 tabWidget->addTab(m_colorTab, i18n("Colors")); 0064 tabWidget->addTab(m_disabledTab, i18n("Disabled")); 0065 tabWidget->setCurrentWidget(m_colorTab); 0066 0067 connect(m_optionTab, &SchemeEditorOptions::changed, this, &SchemeEditorDialog::updateTabs); 0068 connect(m_colorTab, &SchemeEditorColors::changed, this, &SchemeEditorDialog::updateTabs); 0069 connect(m_disabledTab, &SchemeEditorEffects::changed, this, &SchemeEditorDialog::updateTabs); 0070 connect(m_inactiveTab, &SchemeEditorEffects::changed, this, &SchemeEditorDialog::updateTabs); 0071 0072 // "Save" is only shown in overwrite mode 0073 KGuiItem::assign(buttonBox->button(QDialogButtonBox::Apply), KStandardGuiItem::save()); 0074 buttonBox->button(QDialogButtonBox::Apply)->setVisible(false); 0075 buttonBox->button(QDialogButtonBox::Apply)->setEnabled(false); 0076 0077 KGuiItem::assign(buttonBox->button(QDialogButtonBox::Save), KStandardGuiItem::saveAs()); 0078 buttonBox->button(QDialogButtonBox::Reset)->setEnabled(false); 0079 updateTabs(); 0080 } 0081 0082 void SchemeEditorDialog::on_buttonBox_clicked(QAbstractButton *button) 0083 { 0084 if (buttonBox->standardButton(button) == QDialogButtonBox::Reset) { 0085 m_config->markAsClean(); 0086 m_config->reparseConfiguration(); 0087 updateTabs(); 0088 setUnsavedChanges(false); 0089 } else if (buttonBox->standardButton(button) == QDialogButtonBox::Save) { 0090 saveScheme(false /*overwrite*/); 0091 } else if (buttonBox->standardButton(button) == QDialogButtonBox::Apply) { 0092 saveScheme(true /*overwrite*/); 0093 } else if (buttonBox->standardButton(button) == QDialogButtonBox::Close) { 0094 if (m_unsavedChanges) { 0095 KMessageBox::ButtonCode ans = KMessageBox::questionTwoActions(this, 0096 i18n("You have unsaved changes. Do you really want to quit?"), 0097 i18n("Unsaved changes"), 0098 KStandardGuiItem::quit(), 0099 KStandardGuiItem::cancel()); 0100 if (ans == KMessageBox::SecondaryAction) { 0101 return; 0102 } 0103 } 0104 m_config->markAsClean(); 0105 m_config->reparseConfiguration(); 0106 this->accept(); 0107 } 0108 } 0109 0110 void SchemeEditorDialog::saveScheme(bool overwrite) 0111 { 0112 QString name = m_schemeName; 0113 0114 // prompt for the name to save as 0115 if (!overwrite) { 0116 bool ok; 0117 name = QInputDialog::getText(this, i18n("Save Color Scheme"), i18n("&Enter a name for the color scheme:"), QLineEdit::Normal, m_schemeName, &ok); 0118 if (!ok) { 0119 return; 0120 } 0121 } 0122 0123 QString filename = name; 0124 filename.remove(QLatin1Char('\'')); // So Foo's does not become FooS 0125 QRegularExpression fixer(QStringLiteral("[\\W,.-]+(.?)")); 0126 for (auto match = fixer.match(filename); match.hasMatch(); match = fixer.match(filename)) { 0127 filename.replace(match.capturedStart(), match.capturedLength(), match.captured(1).toUpper()); 0128 } 0129 filename.replace(0, 1, filename.at(0).toUpper()); 0130 0131 // check if that name is already in the list 0132 const QString path = QStandardPaths::locate(QStandardPaths::GenericDataLocation, QStringLiteral("color-schemes/") + filename + QStringLiteral(".colors")); 0133 0134 QFile file(path); 0135 const int permissions = file.permissions(); 0136 const bool canWrite = (permissions & QFile::WriteUser); 0137 // or if we can overwrite it if it exists 0138 if (path.isEmpty() || !file.exists() || canWrite) { 0139 if (canWrite && !overwrite) { 0140 int ret = KMessageBox::questionTwoActions(this, 0141 i18n("A color scheme with that name already exists.\nDo you want to overwrite it?"), 0142 i18n("Save Color Scheme"), 0143 KStandardGuiItem::overwrite(), 0144 KStandardGuiItem::cancel()); 0145 0146 // on don't overwrite, call again the function 0147 if (ret == KMessageBox::SecondaryAction) { 0148 this->saveScheme(overwrite); 0149 return; 0150 } 0151 } 0152 0153 // go ahead and save it 0154 QString newpath = QStandardPaths::writableLocation(QStandardPaths::GenericDataLocation) + "/color-schemes/"; 0155 QDir dir; 0156 dir.mkpath(newpath); 0157 newpath += filename + ".colors"; 0158 0159 KConfig *config = m_config->copyTo(newpath); 0160 m_config->markAsClean(); 0161 m_config->reparseConfiguration(); 0162 KConfigGroup group(config, u"General"_s); 0163 group.writeEntry("Name", name); 0164 0165 // sync it and delete pointer 0166 config->sync(); 0167 delete config; 0168 // reopen and update window 0169 m_config = KSharedConfig::openConfig(newpath); 0170 m_schemeName = name; 0171 setWindowTitle(name); 0172 0173 setUnsavedChanges(false); 0174 0175 QTextStream out(stdout); 0176 out << filename << Qt::endl; 0177 } else if (!canWrite && file.exists()) { 0178 KMessageBox::error(this, i18n("You do not have permission to overwrite that scheme"), i18n("Error")); 0179 } 0180 } 0181 0182 void SchemeEditorDialog::updateTabs(bool madeByUser) 0183 { 0184 if (madeByUser) { 0185 setUnsavedChanges(true); 0186 } 0187 KConfigGroup group(m_config, u"ColorEffects:Inactive"_s); 0188 bool showInactiveTab = group.readEntry("Enable", QVariant(true)).toBool(); 0189 0190 const int idx = tabWidget->indexOf(m_inactiveTab); 0191 0192 if (showInactiveTab && idx == -1) { 0193 tabWidget->addTab(m_inactiveTab, i18n("Inactive")); 0194 } else if (!showInactiveTab && idx > -1) { 0195 tabWidget->removeTab(idx); 0196 } 0197 0198 m_optionTab->updateValues(); 0199 m_colorTab->updateValues(); 0200 m_inactiveTab->updateValues(); 0201 m_disabledTab->updateValues(); 0202 } 0203 0204 void SchemeEditorDialog::setUnsavedChanges(bool changes) 0205 { 0206 m_unsavedChanges = changes; 0207 if (changes) { 0208 buttonBox->button(QDialogButtonBox::Apply)->setEnabled(true); 0209 buttonBox->button(QDialogButtonBox::Reset)->setEnabled(true); 0210 } else { 0211 buttonBox->button(QDialogButtonBox::Apply)->setEnabled(false); 0212 buttonBox->button(QDialogButtonBox::Reset)->setEnabled(false); 0213 } 0214 }