File indexing completed on 2024-05-05 05:53:55
0001 /* 0002 SPDX-FileCopyrightText: 2019 Mariusz Glebocki <mglb@arccos-1.net> 0003 0004 Based on KConfigDialog and KConfigDialogManager from KConfigWidgets 0005 0006 SPDX-FileCopyrightText: 2003 Benjamin C Meyer (ben+kdelibs at meyerhome dot net) 0007 SPDX-FileCopyrightText: 2003 Waldo Bastian <bastian@kde.org> 0008 0009 SPDX-License-Identifier: GPL-2.0-or-later 0010 */ 0011 0012 // Own 0013 #include "ConfigDialogButtonGroupManager.h" 0014 0015 // Qt 0016 #include <QAbstractButton> 0017 #include <QButtonGroup> 0018 #include <QString> 0019 #include <QTimer> 0020 0021 using namespace Konsole; 0022 0023 // const QString ConfigDialogButtonGroupManager::ManagedNamePrefix; 0024 const QString ConfigDialogButtonGroupManager::ManagedNamePrefix = QStringLiteral("kcfg_"); 0025 0026 ConfigDialogButtonGroupManager::ConfigDialogButtonGroupManager(QObject *parent, KCoreConfigSkeleton *config) 0027 : QObject(parent) 0028 , _config(config) 0029 { 0030 Q_ASSERT(config); 0031 connect(_config, &KCoreConfigSkeleton::configChanged, this, &ConfigDialogButtonGroupManager::updateWidgets); 0032 } 0033 0034 void ConfigDialogButtonGroupManager::addChildren(const QObject *parentObj) 0035 { 0036 const auto allButtonGroups = parentObj->findChildren<QButtonGroup *>(); 0037 for (const auto *buttonGroup : allButtonGroups) { 0038 if (buttonGroup->objectName().startsWith(ManagedNamePrefix)) { 0039 add(buttonGroup); 0040 } 0041 } 0042 } 0043 0044 void ConfigDialogButtonGroupManager::add(const QButtonGroup *obj) 0045 { 0046 Q_ASSERT(obj->exclusive()); 0047 connect(obj, &QButtonGroup::buttonToggled, this, &ConfigDialogButtonGroupManager::setButtonState, Qt::UniqueConnection); 0048 _groups.append(obj); 0049 } 0050 0051 bool ConfigDialogButtonGroupManager::hasChanged() const 0052 { 0053 for (const QButtonGroup *group : std::as_const(_groups)) { 0054 if (group->checkedButton() == nullptr) { 0055 continue; 0056 } 0057 int value = buttonToEnumValue(group->checkedButton()); 0058 const auto *enumItem = groupToConfigItemEnum(group); 0059 0060 if (enumItem != nullptr && !enumItem->isEqual(value)) { 0061 return true; 0062 } 0063 } 0064 return false; 0065 } 0066 0067 bool ConfigDialogButtonGroupManager::isDefault() const 0068 { 0069 bool useDefaults = _config->useDefaults(true); 0070 bool result = !hasChanged(); 0071 _config->useDefaults(useDefaults); 0072 return result; 0073 } 0074 0075 void ConfigDialogButtonGroupManager::updateWidgets() 0076 { 0077 bool prevSignalsBlocked = signalsBlocked(); 0078 bool changed = false; 0079 blockSignals(true); 0080 for (const QButtonGroup *group : std::as_const(_groups)) { 0081 auto *enumItem = groupToConfigItemEnum(group); 0082 if (enumItem == nullptr) { 0083 continue; 0084 } 0085 0086 int value = enumItem->value(); 0087 const QString &valueName = enumItem->choices().at(value).name; 0088 QAbstractButton *currentButton = nullptr; 0089 for (auto &button : group->buttons()) { 0090 if (button->objectName() == valueName) { 0091 currentButton = button; 0092 break; 0093 } 0094 } 0095 if (currentButton == nullptr) { 0096 return; 0097 } 0098 currentButton->setChecked(true); 0099 changed = true; 0100 } 0101 blockSignals(prevSignalsBlocked); 0102 if (changed) { 0103 QTimer::singleShot(0, this, &ConfigDialogButtonGroupManager::widgetModified); 0104 } 0105 } 0106 0107 void ConfigDialogButtonGroupManager::updateWidgetsDefault() 0108 { 0109 bool useDefaults = _config->useDefaults(true); 0110 updateWidgets(); 0111 _config->useDefaults(useDefaults); 0112 } 0113 0114 void ConfigDialogButtonGroupManager::updateSettings() 0115 { 0116 bool updateConfig = false; 0117 for (const QButtonGroup *group : std::as_const(_groups)) { 0118 auto *enumItem = groupToConfigItemEnum(group); 0119 if (enumItem == nullptr) { 0120 continue; 0121 } 0122 const auto *currentButton = group->checkedButton(); 0123 if (currentButton == nullptr) { 0124 continue; 0125 } 0126 const int value = buttonToEnumValue(currentButton); 0127 if (value < 0) { 0128 continue; 0129 } 0130 0131 if (!enumItem->isEqual(value)) { 0132 enumItem->setValue(value); 0133 updateConfig = true; 0134 } 0135 } 0136 if (updateConfig) { 0137 _config->save(); 0138 Q_EMIT settingsChanged(); 0139 } 0140 } 0141 0142 void ConfigDialogButtonGroupManager::setButtonState(QAbstractButton *button, bool checked) 0143 { 0144 Q_ASSERT(button->group()); 0145 if (!checked) { 0146 // Both deselected and selected buttons trigger this slot, ignore the deselected one 0147 return; 0148 } 0149 auto *enumItem = groupToConfigItemEnum(button->group()); 0150 if (enumItem == nullptr) { 0151 return; 0152 } 0153 0154 int value = buttonToEnumValue(button); 0155 if (value < 0) { 0156 return; 0157 } 0158 0159 Q_EMIT settingsChanged(); 0160 } 0161 0162 // Returns configuration item associated with the group 0163 KCoreConfigSkeleton::ItemEnum *ConfigDialogButtonGroupManager::groupToConfigItemEnum(const QButtonGroup *group) const 0164 { 0165 Q_ASSERT(group); 0166 const QString key = group->objectName().mid(ManagedNamePrefix.length()); 0167 auto *item = _config->findItem(key); 0168 if (item == nullptr) { 0169 return nullptr; 0170 } 0171 auto *enumItem = dynamic_cast<KCoreConfigSkeleton::ItemEnum *>(item); 0172 if (enumItem == nullptr) { 0173 return nullptr; 0174 } 0175 return enumItem; 0176 } 0177 0178 // Returns a value the button represents in its group 0179 int ConfigDialogButtonGroupManager::buttonToEnumValue(const QAbstractButton *button) const 0180 { 0181 Q_ASSERT(button); 0182 Q_ASSERT(button->group()); 0183 0184 if (_buttonValues.contains(button)) { 0185 return _buttonValues[button]; 0186 } 0187 0188 const auto *enumItem = groupToConfigItemEnum(button->group()); 0189 if (enumItem == nullptr) { 0190 return -1; 0191 } 0192 const auto &choices = enumItem->choices(); 0193 0194 const QString buttonName = button->objectName(); 0195 int value = -1; 0196 for (int i = 0; i < choices.size(); ++i) { 0197 if (buttonName == choices.at(i).name) { 0198 value = i; 0199 break; 0200 } 0201 } 0202 _buttonValues[button] = value; 0203 return value; 0204 } 0205 0206 #include "moc_ConfigDialogButtonGroupManager.cpp"