From 18a342ef1446997427de45095109f24c9352296d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Petr=20Mr=C3=A1zek?= Date: Tue, 1 Jul 2014 01:48:09 +0200 Subject: Move settings lib into the main code, fixing error logging in it. --- CMakeLists.txt | 19 ++-- MultiMC.cpp | 8 +- depends/settings/CMakeLists.txt | 41 -------- depends/settings/inifile.cpp | 138 ------------------------- depends/settings/inifile.h | 38 ------- depends/settings/inisettingsobject.cpp | 81 --------------- depends/settings/inisettingsobject.h | 63 ------------ depends/settings/libsettings_config.h | 29 ------ depends/settings/overridesetting.cpp | 30 ------ depends/settings/overridesetting.h | 41 -------- depends/settings/setting.cpp | 53 ---------- depends/settings/setting.h | 119 ---------------------- depends/settings/settingsobject.cpp | 147 --------------------------- depends/settings/settingsobject.h | 179 --------------------------------- gui/dialogs/SettingsDialog.cpp | 2 +- gui/pagedialog/PageDialog.cpp | 2 +- gui/widgets/PageContainer.cpp | 2 +- logic/BaseInstance.cpp | 6 +- logic/BaseInstance.h | 4 +- logic/BaseInstance_p.h | 2 +- logic/InstanceFactory.cpp | 7 +- logic/LegacyInstance.cpp | 2 +- logic/LegacyInstance_p.h | 2 +- logic/Mod.cpp | 2 +- logic/icons/IconList.cpp | 10 +- logic/icons/IconList.h | 4 +- logic/java/JavaUtils.cpp | 2 +- logic/settings/INIFile.cpp | 138 +++++++++++++++++++++++++ logic/settings/INIFile.h | 36 +++++++ logic/settings/INISettingsObject.cpp | 81 +++++++++++++++ logic/settings/INISettingsObject.h | 61 +++++++++++ logic/settings/OverrideSetting.cpp | 30 ++++++ logic/settings/OverrideSetting.h | 39 +++++++ logic/settings/Setting.cpp | 53 ++++++++++ logic/settings/Setting.h | 117 +++++++++++++++++++++ logic/settings/SettingsObject.cpp | 124 +++++++++++++++++++++++ logic/settings/SettingsObject.h | 177 ++++++++++++++++++++++++++++++++ logic/tools/JProfiler.cpp | 2 +- logic/tools/JVisualVM.cpp | 2 +- logic/tools/MCEditTool.cpp | 2 +- logic/updater/UpdateChecker.cpp | 2 +- tests/tst_UpdateChecker.cpp | 4 +- tests/tst_inifile.cpp | 2 +- 43 files changed, 904 insertions(+), 999 deletions(-) delete mode 100644 depends/settings/CMakeLists.txt delete mode 100644 depends/settings/inifile.cpp delete mode 100644 depends/settings/inifile.h delete mode 100644 depends/settings/inisettingsobject.cpp delete mode 100644 depends/settings/inisettingsobject.h delete mode 100644 depends/settings/libsettings_config.h delete mode 100644 depends/settings/overridesetting.cpp delete mode 100644 depends/settings/overridesetting.h delete mode 100644 depends/settings/setting.cpp delete mode 100644 depends/settings/setting.h delete mode 100644 depends/settings/settingsobject.cpp delete mode 100644 depends/settings/settingsobject.h create mode 100644 logic/settings/INIFile.cpp create mode 100644 logic/settings/INIFile.h create mode 100644 logic/settings/INISettingsObject.cpp create mode 100644 logic/settings/INISettingsObject.h create mode 100644 logic/settings/OverrideSetting.cpp create mode 100644 logic/settings/OverrideSetting.h create mode 100644 logic/settings/Setting.cpp create mode 100644 logic/settings/Setting.h create mode 100644 logic/settings/SettingsObject.cpp create mode 100644 logic/settings/SettingsObject.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 9304547b..bd670573 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -252,11 +252,6 @@ add_definitions(-DLIBUTIL_STATIC) add_subdirectory(depends/util) include_directories(${LIBUTIL_INCLUDE_DIR}) -# Add the settings library. -add_definitions(-DLIBSETTINGS_STATIC) -add_subdirectory(depends/settings) -include_directories(${LIBSETTINGS_INCLUDE_DIR}) - # Add the updater add_subdirectory(mmc_updater) @@ -553,6 +548,18 @@ SET(MULTIMC_SOURCES logic/tasks/SequentialTask.h logic/tasks/SequentialTask.cpp + # Settings + logic/settings/INIFile.cpp + logic/settings/INIFile.h + logic/settings/INISettingsObject.cpp + logic/settings/INISettingsObject.h + logic/settings/OverrideSetting.cpp + logic/settings/OverrideSetting.h + logic/settings/Setting.cpp + logic/settings/Setting.h + logic/settings/SettingsObject.cpp + logic/settings/SettingsObject.h + # Java related code logic/java/JavaChecker.h logic/java/JavaChecker.cpp @@ -698,7 +705,7 @@ add_executable(MultiMC MACOSX_BUNDLE WIN32 main.cpp ${MULTIMC_RCS}) # Link target_link_libraries(MultiMC MultiMC_common) -target_link_libraries(MultiMC_common xz-embedded unpack200 quazip libUtil libSettings ${MultiMC_LINK_ADDITIONAL_LIBS}) +target_link_libraries(MultiMC_common xz-embedded unpack200 quazip libUtil ${MultiMC_LINK_ADDITIONAL_LIBS}) qt5_use_modules(MultiMC Core Widgets Network Xml Concurrent ${MultiMC_QT_ADDITIONAL_MODULES}) qt5_use_modules(MultiMC_common Core Widgets Network Xml Concurrent ${MultiMC_QT_ADDITIONAL_MODULES}) diff --git a/MultiMC.cpp b/MultiMC.cpp index bd72c139..7e7c6c88 100644 --- a/MultiMC.cpp +++ b/MultiMC.cpp @@ -42,10 +42,10 @@ #include "pathutils.h" #include "cmdutils.h" -#include -#include +#include "logic/settings/INISettingsObject.h" +#include "logic/settings/Setting.h" #include "logger/QsLog.h" -#include +#include "logger/QsLogDest.h" #ifdef Q_OS_WIN32 #include @@ -219,7 +219,7 @@ MultiMC::MultiMC(int &argc, char **argv, bool root_override) m_instances.reset(new InstanceList(InstDirSetting->get().toString(), this)); QLOG_INFO() << "Loading Instances..."; m_instances->loadList(); - connect(InstDirSetting.get(), SIGNAL(settingChanged(const Setting &, QVariant)), + connect(InstDirSetting.get(), SIGNAL(SettingChanged(const Setting &, QVariant)), m_instances.get(), SLOT(on_InstFolderChanged(const Setting &, QVariant))); // and accounts diff --git a/depends/settings/CMakeLists.txt b/depends/settings/CMakeLists.txt deleted file mode 100644 index 346e15b5..00000000 --- a/depends/settings/CMakeLists.txt +++ /dev/null @@ -1,41 +0,0 @@ -project(libSettings) - -# Find Qt -find_package(Qt5Core REQUIRED) - -# Include Qt headers. -include_directories(${Qt5Base_INCLUDE_DIRS}) - -include(UseCXX11) -include(Coverage) - -set(LIBSETTINGS_SOURCES - libsettings_config.h - - inifile.h - inifile.cpp - - settingsobject.h - settingsobject.cpp - inisettingsobject.h - inisettingsobject.cpp - - setting.h - setting.cpp - overridesetting.h - overridesetting.cpp -) - -# Set the include dir path. -set(LIBSETTINGS_INCLUDE_DIR "${CMAKE_CURRENT_SOURCE_DIR}" PARENT_SCOPE) - -# Static link! -add_definitions(-DLIBSETTINGS_STATIC) - -add_definitions(-DLIBSETTINGS_LIBRARY) - -set(CMAKE_POSITION_INDEPENDENT_CODE ON) - -add_library(libSettings STATIC ${LIBSETTINGS_SOURCES}) -qt5_use_modules(libSettings Core) -target_link_libraries(libSettings) diff --git a/depends/settings/inifile.cpp b/depends/settings/inifile.cpp deleted file mode 100644 index b2098913..00000000 --- a/depends/settings/inifile.cpp +++ /dev/null @@ -1,138 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "inifile.h" - -#include -#include -#include - -INIFile::INIFile() -{ -} - -QString INIFile::unescape(QString orig) -{ - QString out; - QChar prev = 0; - for(auto c: orig) - { - if(prev == '\\') - { - if(c == 'n') - out += '\n'; - else if (c == 't') - out += '\t'; - else - out += c; - prev = 0; - } - else - { - if(c == '\\') - { - prev = c; - continue; - } - out += c; - prev = 0; - } - } - return out; -} - -QString INIFile::escape(QString orig) -{ - QString out; - for(auto c: orig) - { - if(c == '\n') - out += "\\n"; - else if (c == '\t') - out += "\\t"; - else if(c == '\\') - out += "\\\\"; - else - out += c; - } - return out; -} - -bool INIFile::saveFile(QString fileName) -{ - // TODO Handle errors. - QFile file(fileName); - file.open(QIODevice::WriteOnly); - QTextStream out(&file); - out.setCodec("UTF-8"); - - for (Iterator iter = begin(); iter != end(); iter++) - { - QString value = iter.value().toString(); - value = escape(value); - out << iter.key() << "=" << value << "\n"; - } - - return true; -} - -bool INIFile::loadFile(QString fileName) -{ - QFile file(fileName); - if (!file.open(QIODevice::ReadOnly)) - return false; - bool success = loadFile(file.readAll()); - file.close(); - return success; -} -bool INIFile::loadFile(QByteArray file) -{ - QTextStream in(file); - in.setCodec("UTF-8"); - - QStringList lines = in.readAll().split('\n'); - for (int i = 0; i < lines.count(); i++) - { - QString &lineRaw = lines[i]; - // Ignore comments. - QString line = lineRaw.left(lineRaw.indexOf('#')).trimmed(); - - int eqPos = line.indexOf('='); - if (eqPos == -1) - continue; - QString key = line.left(eqPos).trimmed(); - QString valueStr = line.right(line.length() - eqPos - 1).trimmed(); - - valueStr = unescape(valueStr); - - QVariant value(valueStr); - this->operator[](key) = value; - } - - return true; -} - -QVariant INIFile::get(QString key, QVariant def) const -{ - if (!this->contains(key)) - return def; - else - return this->operator[](key); -} - -void INIFile::set(QString key, QVariant val) -{ - this->operator[](key) = val; -} diff --git a/depends/settings/inifile.h b/depends/settings/inifile.h deleted file mode 100644 index 4fb0054d..00000000 --- a/depends/settings/inifile.h +++ /dev/null @@ -1,38 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#pragma once - -#include -#include -#include - -#include "libsettings_config.h" - -// Sectionless INI parser (for instance config files) -class LIBSETTINGS_EXPORT INIFile : public QMap -{ -public: - explicit INIFile(); - - bool loadFile(QByteArray file); - bool loadFile(QString fileName); - bool saveFile(QString fileName); - - QVariant get(QString key, QVariant def) const; - void set(QString key, QVariant val); - static QString unescape(QString orig); - static QString escape(QString orig); -}; diff --git a/depends/settings/inisettingsobject.cpp b/depends/settings/inisettingsobject.cpp deleted file mode 100644 index 2cee8e3c..00000000 --- a/depends/settings/inisettingsobject.cpp +++ /dev/null @@ -1,81 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "inisettingsobject.h" -#include "setting.h" - -INISettingsObject::INISettingsObject(const QString &path, QObject *parent) - : SettingsObject(parent) -{ - m_filePath = path; - m_ini.loadFile(path); -} - -void INISettingsObject::setFilePath(const QString &filePath) -{ - m_filePath = filePath; -} - -bool INISettingsObject::reload() -{ - return m_ini.loadFile(m_filePath) && SettingsObject::reload(); -} - -void INISettingsObject::changeSetting(const Setting &setting, QVariant value) -{ - if (contains(setting.id())) - { - // valid value -> set the main config, remove all the sysnonyms - if (value.isValid()) - { - auto list = setting.configKeys(); - m_ini.set(list.takeFirst(), value); - for(auto iter: list) - m_ini.remove(iter); - } - // invalid -> remove all (just like resetSetting) - else - { - for(auto iter: setting.configKeys()) - m_ini.remove(iter); - } - m_ini.saveFile(m_filePath); - } -} - -void INISettingsObject::resetSetting(const Setting &setting) -{ - // if we have the setting, remove all the synonyms. ALL OF THEM - if (contains(setting.id())) - { - for(auto iter: setting.configKeys()) - m_ini.remove(iter); - m_ini.saveFile(m_filePath); - } -} - -QVariant INISettingsObject::retrieveValue(const Setting &setting) -{ - // if we have the setting, return value of the first matching synonym - if (contains(setting.id())) - { - for(auto iter: setting.configKeys()) - { - if(m_ini.contains(iter)) - return m_ini[iter]; - } - } - return QVariant(); -} diff --git a/depends/settings/inisettingsobject.h b/depends/settings/inisettingsobject.h deleted file mode 100644 index 12370896..00000000 --- a/depends/settings/inisettingsobject.h +++ /dev/null @@ -1,63 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#pragma once - -#include - -#include "inifile.h" - -#include "settingsobject.h" - -#include "libsettings_config.h" - -/*! - * \brief A settings object that stores its settings in an INIFile. - */ -class LIBSETTINGS_EXPORT INISettingsObject : public SettingsObject -{ - Q_OBJECT -public: - explicit INISettingsObject(const QString &path, QObject *parent = 0); - - /*! - * \brief Gets the path to the INI file. - * \return The path to the INI file. - */ - virtual QString filePath() const - { - return m_filePath; - } - - /*! - * \brief Sets the path to the INI file and reloads it. - * \param filePath The INI file's new path. - */ - virtual void setFilePath(const QString &filePath); - - bool reload() override; - -protected -slots: - virtual void changeSetting(const Setting &setting, QVariant value); - virtual void resetSetting(const Setting &setting); - -protected: - virtual QVariant retrieveValue(const Setting &setting); - - INIFile m_ini; - - QString m_filePath; -}; diff --git a/depends/settings/libsettings_config.h b/depends/settings/libsettings_config.h deleted file mode 100644 index e5beed28..00000000 --- a/depends/settings/libsettings_config.h +++ /dev/null @@ -1,29 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#pragma once - -#include - -#ifdef LIBSETTINGS_STATIC -#define LIBSETTINGS_EXPORT -#else -#ifdef LIBSETTINGS_LIBRARY -#define LIBSETTINGS_EXPORT Q_DECL_EXPORT -#else -#define LIBSETTINGS_EXPORT Q_DECL_IMPORT -#endif -#endif - diff --git a/depends/settings/overridesetting.cpp b/depends/settings/overridesetting.cpp deleted file mode 100644 index 7b5f5418..00000000 --- a/depends/settings/overridesetting.cpp +++ /dev/null @@ -1,30 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "overridesetting.h" - -OverrideSetting::OverrideSetting(std::shared_ptr other) - : Setting(other->configKeys(), QVariant()) -{ - m_other = other; -} - -QVariant OverrideSetting::defValue() const -{ - if (m_other) - return m_other->get(); - else - return QVariant(); -} diff --git a/depends/settings/overridesetting.h b/depends/settings/overridesetting.h deleted file mode 100644 index 5ef901d0..00000000 --- a/depends/settings/overridesetting.h +++ /dev/null @@ -1,41 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#pragma once - -#include -#include - -#include "setting.h" - -#include "libsettings_config.h" - -/*! - * \brief A setting that 'overrides another.' - * This means that the setting's default value will be the value of another setting. - * The other setting can be (and usually is) a part of a different SettingsObject - * than this one. - */ -class LIBSETTINGS_EXPORT OverrideSetting : public Setting -{ - Q_OBJECT -public: - explicit OverrideSetting(std::shared_ptr other); - - virtual QVariant defValue() const; - -protected: - std::shared_ptr m_other; -}; diff --git a/depends/settings/setting.cpp b/depends/settings/setting.cpp deleted file mode 100644 index 0d685771..00000000 --- a/depends/settings/setting.cpp +++ /dev/null @@ -1,53 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "setting.h" -#include "settingsobject.h" - -Setting::Setting(QStringList synonyms, QVariant defVal) - : QObject(), m_synonyms(synonyms), m_defVal(defVal) -{ -} - -QVariant Setting::get() const -{ - SettingsObject *sbase = m_storage; - if (!sbase) - { - return defValue(); - } - else - { - QVariant test = sbase->retrieveValue(*this); - if (!test.isValid()) - return defValue(); - return test; - } -} - -QVariant Setting::defValue() const -{ - return m_defVal; -} - -void Setting::set(QVariant value) -{ - emit settingChanged(*this, value); -} - -void Setting::reset() -{ - emit settingReset(*this); -} diff --git a/depends/settings/setting.h b/depends/settings/setting.h deleted file mode 100644 index a73474d2..00000000 --- a/depends/settings/setting.h +++ /dev/null @@ -1,119 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#pragma once - -#include -#include -#include -#include - -#include "libsettings_config.h" - -class SettingsObject; - -/*! - * - */ -class LIBSETTINGS_EXPORT Setting : public QObject -{ - Q_OBJECT -public: - /** - * Construct a Setting - * - * Synonyms are all the possible names used in the settings object, in order of preference. - * First synonym is the ID, which identifies the setting in MultiMC. - * - * defVal is the default value that will be returned when the settings object - * doesn't have any value for this setting. - */ - explicit Setting(QStringList synonyms, QVariant defVal = QVariant()); - - /*! - * \brief Gets this setting's ID. - * This is used to refer to the setting within the application. - * \warning Changing the ID while the setting is registered with a SettingsObject results in - * undefined behavior. - * \return The ID of the setting. - */ - virtual QString id() const - { - return m_synonyms.first(); - } - - /*! - * \brief Gets this setting's config file key. - * This is used to store the setting's value in the config file. It is usually - * the same as the setting's ID, but it can be different. - * \return The setting's config file key. - */ - virtual QStringList configKeys() const - { - return m_synonyms; - } - - /*! - * \brief Gets this setting's value as a QVariant. - * This is done by calling the SettingsObject's retrieveValue() function. - * If this Setting doesn't have a SettingsObject, this returns an invalid QVariant. - * \return QVariant containing this setting's value. - * \sa value() - */ - virtual QVariant get() const; - - /*! - * \brief Gets this setting's default value. - * \return The default value of this setting. - */ - virtual QVariant defValue() const; - -signals: - /*! - * \brief Signal emitted when this Setting object's value changes. - * \param setting A reference to the Setting that changed. - * \param value This Setting object's new value. - */ - void settingChanged(const Setting &setting, QVariant value); - - /*! - * \brief Signal emitted when this Setting object's value resets to default. - * \param setting A reference to the Setting that changed. - */ - void settingReset(const Setting &setting); - -public -slots: - /*! - * \brief Changes the setting's value. - * This is done by emitting the settingChanged() signal which will then be - * handled by the SettingsObject object and cause the setting to change. - * \param value The new value. - */ - virtual void set(QVariant value); - - /*! - * \brief Reset the setting to default - * This is done by emitting the settingReset() signal which will then be - * handled by the SettingsObject object and cause the setting to change. - */ - virtual void reset(); - -protected: - friend class SettingsObject; - SettingsObject * m_storage; - QStringList m_synonyms; - QVariant m_defVal; -}; diff --git a/depends/settings/settingsobject.cpp b/depends/settings/settingsobject.cpp deleted file mode 100644 index 0e3030df..00000000 --- a/depends/settings/settingsobject.cpp +++ /dev/null @@ -1,147 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include "settingsobject.h" -#include "setting.h" -#include "overridesetting.h" - -#include - -SettingsObject::SettingsObject(QObject *parent) : QObject(parent) -{ -} - -SettingsObject::~SettingsObject() -{ - m_settings.clear(); -} - -std::shared_ptr SettingsObject::registerOverride(std::shared_ptr original) -{ - if (contains(original->id())) - { - qDebug(QString("Failed to register setting %1. ID already exists.") - .arg(original->id()) - .toUtf8()); - return nullptr; // Fail - } - auto override = std::make_shared(original); - override->m_storage = this; - connectSignals(*override); - m_settings.insert(override->id(), override); - return override; -} - -std::shared_ptr SettingsObject::registerSetting(QStringList synonyms, QVariant defVal) -{ - if (synonyms.empty()) - return nullptr; - if (contains(synonyms.first())) - { - qDebug(QString("Failed to register setting %1. ID already exists.") - .arg(synonyms.first()) - .toUtf8()); - return nullptr; // Fail - } - auto setting = std::make_shared(synonyms, defVal); - setting->m_storage = this; - connectSignals(*setting); - m_settings.insert(setting->id(), setting); - return setting; -} - -/* - -bool SettingsObject::registerSetting(Setting *setting) -{ - if (contains(setting->id())) - { - qDebug(QString("Failed to register setting %1. ID already exists.") - .arg(setting->id()) - .toUtf8()); - return false; // Fail - } - - m_settings.insert(setting->id(), setting); - setting->setParent(this); // Take ownership. - - // Connect signals. - connectSignals(*setting); - - // qDebug(QString("Registered setting %1.").arg(setting->id()).toUtf8()); - return true; -} -*/ -std::shared_ptr SettingsObject::getSetting(const QString &id) const -{ - // Make sure there is a setting with the given ID. - if (!m_settings.contains(id)) - return NULL; - - return m_settings[id]; -} - -QVariant SettingsObject::get(const QString &id) const -{ - auto setting = getSetting(id); - return (setting ? setting->get() : QVariant()); -} - -bool SettingsObject::set(const QString &id, QVariant value) -{ - auto setting = getSetting(id); - if (!setting) - { - qDebug(QString("Error changing setting %1. Setting doesn't exist.").arg(id).toUtf8()); - return false; - } - else - { - setting->set(value); - return true; - } -} - -void SettingsObject::reset(const QString &id) const -{ - auto setting = getSetting(id); - if (setting) - setting->reset(); -} - -bool SettingsObject::contains(const QString &id) -{ - return m_settings.contains(id); -} - -bool SettingsObject::reload() -{ - for (auto setting : m_settings.values()) - { - setting->set(setting->get()); - } - return true; -} - -void SettingsObject::connectSignals(const Setting &setting) -{ - connect(&setting, SIGNAL(settingChanged(const Setting &, QVariant)), - SLOT(changeSetting(const Setting &, QVariant))); - connect(&setting, SIGNAL(settingChanged(const Setting &, QVariant)), - SIGNAL(settingChanged(const Setting &, QVariant))); - - connect(&setting, SIGNAL(settingReset(Setting)), SLOT(resetSetting(const Setting &))); - connect(&setting, SIGNAL(settingReset(Setting)), SIGNAL(settingReset(const Setting &))); -} diff --git a/depends/settings/settingsobject.h b/depends/settings/settingsobject.h deleted file mode 100644 index b1b26b09..00000000 --- a/depends/settings/settingsobject.h +++ /dev/null @@ -1,179 +0,0 @@ -/* Copyright 2013 MultiMC Contributors - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#pragma once - -#include -#include -#include -#include -#include - -#include "libsettings_config.h" - -class Setting; - -/*! - * \brief The SettingsObject handles communicating settings between the application and a - *settings file. - * The class keeps a list of Setting objects. Each Setting object represents one - * of the application's settings. These Setting objects are registered with - * a SettingsObject and can be managed similarly to the way a list works. - * - * \author Andrew Okin - * \date 2/22/2013 - * - * \sa Setting - */ -class LIBSETTINGS_EXPORT SettingsObject : public QObject -{ - Q_OBJECT -public: - explicit SettingsObject(QObject *parent = 0); - virtual ~SettingsObject(); - /*! - * Registers an override setting for the given original setting in this settings object - * - * This will fail if there is already a setting with the same ID as - * the one that is being registered. - * \return A valid Setting shared pointer if successful. - */ - std::shared_ptr registerOverride(std::shared_ptr original); - - /*! - * Registers the given setting with this SettingsObject and connects the necessary signals. - * - * This will fail if there is already a setting with the same ID as - * the one that is being registered. - * \return A valid Setting shared pointer if successful. - */ - std::shared_ptr registerSetting(QStringList synonyms, - QVariant defVal = QVariant()); - - /*! - * Registers the given setting with this SettingsObject and connects the necessary signals. - * - * This will fail if there is already a setting with the same ID as - * the one that is being registered. - * \return A valid Setting shared pointer if successful. - */ - std::shared_ptr registerSetting(QString id, QVariant defVal = QVariant()) - { - return registerSetting(QStringList(id), defVal); - } - - /*! - * \brief Gets the setting with the given ID. - * \param id The ID of the setting to get. - * \return A pointer to the setting with the given ID. - * Returns null if there is no setting with the given ID. - * \sa operator []() - */ - std::shared_ptr getSetting(const QString &id) const; - - /*! - * \brief Gets the value of the setting with the given ID. - * \param id The ID of the setting to get. - * \return The setting's value as a QVariant. - * If no setting with the given ID exists, returns an invalid QVariant. - */ - QVariant get(const QString &id) const; - - /*! - * \brief Sets the value of the setting with the given ID. - * If no setting with the given ID exists, returns false and logs to qDebug - * \param id The ID of the setting to change. - * \param value The new value of the setting. - * \return True if successful, false if it failed. - */ - bool set(const QString &id, QVariant value); - - /*! - * \brief Reverts the setting with the given ID to default. - * \param id The ID of the setting to reset. - */ - void reset(const QString &id) const; - - /*! - * \brief Checks if this SettingsObject contains a setting with the given ID. - * \param id The ID to check for. - * \return True if the SettingsObject has a setting with the given ID. - */ - bool contains(const QString &id); - - /*! - * \brief Reloads the settings and emit signals for changed settings - * \return True if reloading was successful - */ - virtual bool reload(); - -signals: - /*! - * \brief Signal emitted when one of this SettingsObject object's settings changes. - * This is usually just connected directly to each Setting object's - * settingChanged() signals. - * \param setting A reference to the Setting object that changed. - * \param value The Setting object's new value. - */ - void settingChanged(const Setting &setting, QVariant value); - - /*! - * \brief Signal emitted when one of this SettingsObject object's settings resets. - * This is usually just connected directly to each Setting object's - * settingReset() signals. - * \param setting A reference to the Setting object that changed. - */ - void settingReset(const Setting &setting); - -protected -slots: - /*! - * \brief Changes a setting. - * This slot is usually connected to each Setting object's - * settingChanged() signal. The signal is emitted, causing this slot - * to update the setting's value in the config file. - * \param setting A reference to the Setting object that changed. - * \param value The setting's new value. - */ - virtual void changeSetting(const Setting &setting, QVariant value) = 0; - - /*! - * \brief Resets a setting. - * This slot is usually connected to each Setting object's - * settingReset() signal. The signal is emitted, causing this slot - * to update the setting's value in the config file. - * \param setting A reference to the Setting object that changed. - */ - virtual void resetSetting(const Setting &setting) = 0; - -protected: - /*! - * \brief Connects the necessary signals to the given Setting. - * \param setting The setting to connect. - */ - void connectSignals(const Setting &setting); - - /*! - * \brief Function used by Setting objects to get their values from the SettingsObject. - * \param setting The - * \return - */ - virtual QVariant retrieveValue(const Setting &setting) = 0; - - friend class Setting; - -private: - QMap> m_settings; -}; diff --git a/gui/dialogs/SettingsDialog.cpp b/gui/dialogs/SettingsDialog.cpp index 87da0c68..5108daa2 100644 --- a/gui/dialogs/SettingsDialog.cpp +++ b/gui/dialogs/SettingsDialog.cpp @@ -32,7 +32,7 @@ #include "logic/tools/BaseProfiler.h" -#include +#include "logic/settings/SettingsObject.h" #include #include #include diff --git a/gui/pagedialog/PageDialog.cpp b/gui/pagedialog/PageDialog.cpp index 07027a84..4dd4a811 100644 --- a/gui/pagedialog/PageDialog.cpp +++ b/gui/pagedialog/PageDialog.cpp @@ -16,7 +16,7 @@ #include "PageDialog.h" #include "gui/Platform.h" #include "MultiMC.h" -#include +#include "logic/settings/SettingsObject.h" #include #include diff --git a/gui/widgets/PageContainer.cpp b/gui/widgets/PageContainer.cpp index 237e7224..928e15dd 100644 --- a/gui/widgets/PageContainer.cpp +++ b/gui/widgets/PageContainer.cpp @@ -27,7 +27,7 @@ #include #include #include -#include +#include "logic/settings/SettingsObject.h" #include "PageContainer_p.h" #include diff --git a/logic/BaseInstance.cpp b/logic/BaseInstance.cpp index 15bf5ab6..9a811577 100644 --- a/logic/BaseInstance.cpp +++ b/logic/BaseInstance.cpp @@ -21,9 +21,9 @@ #include #include "MultiMC.h" -#include "inisettingsobject.h" -#include "setting.h" -#include "overridesetting.h" +#include "logic/settings/INISettingsObject.h" +#include "logic/settings/Setting.h" +#include "logic/settings/OverrideSetting.h" #include "pathutils.h" #include diff --git a/logic/BaseInstance.h b/logic/BaseInstance.h index 5f5378e7..0cd17de9 100644 --- a/logic/BaseInstance.h +++ b/logic/BaseInstance.h @@ -19,9 +19,9 @@ #include #include -#include +#include "logic/settings/SettingsObject.h" -#include "inifile.h" +#include "logic/settings/INIFile.h" #include "logic/BaseVersionList.h" #include "logic/auth/MojangAccount.h" diff --git a/logic/BaseInstance_p.h b/logic/BaseInstance_p.h index 6498454f..77486abc 100644 --- a/logic/BaseInstance_p.h +++ b/logic/BaseInstance_p.h @@ -18,7 +18,7 @@ #include #include -#include +#include "logic/settings/SettingsObject.h" #include "BaseInstance.h" diff --git a/logic/InstanceFactory.cpp b/logic/InstanceFactory.cpp index c0a392e0..f0f7ffb3 100644 --- a/logic/InstanceFactory.cpp +++ b/logic/InstanceFactory.cpp @@ -15,9 +15,10 @@ #include #include -#include -#include -#include + +#include "logic/settings/INIFile.h" +#include "logic/settings/INISettingsObject.h" +#include "logic/settings/Setting.h" #include #include "logger/QsLog.h" diff --git a/logic/LegacyInstance.cpp b/logic/LegacyInstance.cpp index 5c15616a..e3054b27 100644 --- a/logic/LegacyInstance.cpp +++ b/logic/LegacyInstance.cpp @@ -16,7 +16,7 @@ #include #include #include -#include +#include #include #include diff --git a/logic/LegacyInstance_p.h b/logic/LegacyInstance_p.h index 061847de..50862027 100644 --- a/logic/LegacyInstance_p.h +++ b/logic/LegacyInstance_p.h @@ -15,7 +15,7 @@ #pragma once #include -#include +#include "logic/settings/SettingsObject.h" #include #include "BaseInstance_p.h" diff --git a/logic/Mod.cpp b/logic/Mod.cpp index c6872d6e..534fa796 100644 --- a/logic/Mod.cpp +++ b/logic/Mod.cpp @@ -24,7 +24,7 @@ #include "Mod.h" #include -#include +#include "logic/settings/INIFile.h" #include "logger/QsLog.h" Mod::Mod(const QFileInfo &file) diff --git a/logic/icons/IconList.cpp b/logic/icons/IconList.cpp index 829fc5fc..872d5a8a 100644 --- a/logic/icons/IconList.cpp +++ b/logic/icons/IconList.cpp @@ -15,14 +15,14 @@ #include "IconList.h" #include -#include +#include "logic/settings/SettingsObject.h" #include #include #include #include #include #include -#include +#include #define MAX_SIZE 1024 @@ -45,8 +45,8 @@ IconList::IconList(QObject *parent) : QAbstractListModel(parent) auto setting = MMC->settings()->getSetting("IconsDir"); QString path = setting->get().toString(); - connect(setting.get(), SIGNAL(settingChanged(const Setting &, QVariant)), - SLOT(settingChanged(const Setting &, QVariant))); + connect(setting.get(), SIGNAL(SettingChanged(const Setting &, QVariant)), + SLOT(SettingChanged(const Setting &, QVariant))); directoryChanged(path); } @@ -143,7 +143,7 @@ void IconList::fileChanged(const QString &path) emit iconUpdated(key); } -void IconList::settingChanged(const Setting &setting, QVariant value) +void IconList::SettingChanged(const Setting &setting, QVariant value) { if(setting.id() != "IconsDir") return; diff --git a/logic/icons/IconList.h b/logic/icons/IconList.h index 4ee3f782..e3ff9fab 100644 --- a/logic/icons/IconList.h +++ b/logic/icons/IconList.h @@ -22,7 +22,7 @@ #include #include #include "MMCIcon.h" -#include "setting.h" +#include "logic/settings/Setting.h" class QFileSystemWatcher; @@ -68,7 +68,7 @@ protected slots: void directoryChanged(const QString &path); void fileChanged(const QString &path); - void settingChanged(const Setting & setting, QVariant value); + void SettingChanged(const Setting & setting, QVariant value); private: std::shared_ptr m_watcher; bool is_watching; diff --git a/logic/java/JavaUtils.cpp b/logic/java/JavaUtils.cpp index 09719c73..2b11ddb9 100644 --- a/logic/java/JavaUtils.cpp +++ b/logic/java/JavaUtils.cpp @@ -18,7 +18,7 @@ #include #include -#include +#include #include #include "MultiMC.h" diff --git a/logic/settings/INIFile.cpp b/logic/settings/INIFile.cpp new file mode 100644 index 00000000..9cf76c0a --- /dev/null +++ b/logic/settings/INIFile.cpp @@ -0,0 +1,138 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "logic/settings/INIFile.h" + +#include +#include +#include + +INIFile::INIFile() +{ +} + +QString INIFile::unescape(QString orig) +{ + QString out; + QChar prev = 0; + for(auto c: orig) + { + if(prev == '\\') + { + if(c == 'n') + out += '\n'; + else if (c == 't') + out += '\t'; + else + out += c; + prev = 0; + } + else + { + if(c == '\\') + { + prev = c; + continue; + } + out += c; + prev = 0; + } + } + return out; +} + +QString INIFile::escape(QString orig) +{ + QString out; + for(auto c: orig) + { + if(c == '\n') + out += "\\n"; + else if (c == '\t') + out += "\\t"; + else if(c == '\\') + out += "\\\\"; + else + out += c; + } + return out; +} + +bool INIFile::saveFile(QString fileName) +{ + // TODO Handle errors. + QFile file(fileName); + file.open(QIODevice::WriteOnly); + QTextStream out(&file); + out.setCodec("UTF-8"); + + for (Iterator iter = begin(); iter != end(); iter++) + { + QString value = iter.value().toString(); + value = escape(value); + out << iter.key() << "=" << value << "\n"; + } + + return true; +} + +bool INIFile::loadFile(QString fileName) +{ + QFile file(fileName); + if (!file.open(QIODevice::ReadOnly)) + return false; + bool success = loadFile(file.readAll()); + file.close(); + return success; +} +bool INIFile::loadFile(QByteArray file) +{ + QTextStream in(file); + in.setCodec("UTF-8"); + + QStringList lines = in.readAll().split('\n'); + for (int i = 0; i < lines.count(); i++) + { + QString &lineRaw = lines[i]; + // Ignore comments. + QString line = lineRaw.left(lineRaw.indexOf('#')).trimmed(); + + int eqPos = line.indexOf('='); + if (eqPos == -1) + continue; + QString key = line.left(eqPos).trimmed(); + QString valueStr = line.right(line.length() - eqPos - 1).trimmed(); + + valueStr = unescape(valueStr); + + QVariant value(valueStr); + this->operator[](key) = value; + } + + return true; +} + +QVariant INIFile::get(QString key, QVariant def) const +{ + if (!this->contains(key)) + return def; + else + return this->operator[](key); +} + +void INIFile::set(QString key, QVariant val) +{ + this->operator[](key) = val; +} diff --git a/logic/settings/INIFile.h b/logic/settings/INIFile.h new file mode 100644 index 00000000..991198e6 --- /dev/null +++ b/logic/settings/INIFile.h @@ -0,0 +1,36 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#pragma once + +#include +#include +#include + +// Sectionless INI parser (for instance config files) +class INIFile : public QMap +{ +public: + explicit INIFile(); + + bool loadFile(QByteArray file); + bool loadFile(QString fileName); + bool saveFile(QString fileName); + + QVariant get(QString key, QVariant def) const; + void set(QString key, QVariant val); + static QString unescape(QString orig); + static QString escape(QString orig); +}; diff --git a/logic/settings/INISettingsObject.cpp b/logic/settings/INISettingsObject.cpp new file mode 100644 index 00000000..eb5e6dd4 --- /dev/null +++ b/logic/settings/INISettingsObject.cpp @@ -0,0 +1,81 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "INISettingsObject.h" +#include "Setting.h" + +INISettingsObject::INISettingsObject(const QString &path, QObject *parent) + : SettingsObject(parent) +{ + m_filePath = path; + m_ini.loadFile(path); +} + +void INISettingsObject::setFilePath(const QString &filePath) +{ + m_filePath = filePath; +} + +bool INISettingsObject::reload() +{ + return m_ini.loadFile(m_filePath) && SettingsObject::reload(); +} + +void INISettingsObject::changeSetting(const Setting &setting, QVariant value) +{ + if (contains(setting.id())) + { + // valid value -> set the main config, remove all the sysnonyms + if (value.isValid()) + { + auto list = setting.configKeys(); + m_ini.set(list.takeFirst(), value); + for(auto iter: list) + m_ini.remove(iter); + } + // invalid -> remove all (just like resetSetting) + else + { + for(auto iter: setting.configKeys()) + m_ini.remove(iter); + } + m_ini.saveFile(m_filePath); + } +} + +void INISettingsObject::resetSetting(const Setting &setting) +{ + // if we have the setting, remove all the synonyms. ALL OF THEM + if (contains(setting.id())) + { + for(auto iter: setting.configKeys()) + m_ini.remove(iter); + m_ini.saveFile(m_filePath); + } +} + +QVariant INISettingsObject::retrieveValue(const Setting &setting) +{ + // if we have the setting, return value of the first matching synonym + if (contains(setting.id())) + { + for(auto iter: setting.configKeys()) + { + if(m_ini.contains(iter)) + return m_ini[iter]; + } + } + return QVariant(); +} diff --git a/logic/settings/INISettingsObject.h b/logic/settings/INISettingsObject.h new file mode 100644 index 00000000..86b4b098 --- /dev/null +++ b/logic/settings/INISettingsObject.h @@ -0,0 +1,61 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#pragma once + +#include + +#include "logic/settings/INIFile.h" + +#include "logic/settings/SettingsObject.h" + +/*! + * \brief A settings object that stores its settings in an INIFile. + */ +class INISettingsObject : public SettingsObject +{ + Q_OBJECT +public: + explicit INISettingsObject(const QString &path, QObject *parent = 0); + + /*! + * \brief Gets the path to the INI file. + * \return The path to the INI file. + */ + virtual QString filePath() const + { + return m_filePath; + } + + /*! + * \brief Sets the path to the INI file and reloads it. + * \param filePath The INI file's new path. + */ + virtual void setFilePath(const QString &filePath); + + bool reload() override; + +protected +slots: + virtual void changeSetting(const Setting &setting, QVariant value); + virtual void resetSetting(const Setting &setting); + +protected: + virtual QVariant retrieveValue(const Setting &setting); + + INIFile m_ini; + + QString m_filePath; +}; diff --git a/logic/settings/OverrideSetting.cpp b/logic/settings/OverrideSetting.cpp new file mode 100644 index 00000000..69d976bd --- /dev/null +++ b/logic/settings/OverrideSetting.cpp @@ -0,0 +1,30 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "OverrideSetting.h" + +OverrideSetting::OverrideSetting(std::shared_ptr other) + : Setting(other->configKeys(), QVariant()) +{ + m_other = other; +} + +QVariant OverrideSetting::defValue() const +{ + if (m_other) + return m_other->get(); + else + return QVariant(); +} diff --git a/logic/settings/OverrideSetting.h b/logic/settings/OverrideSetting.h new file mode 100644 index 00000000..1d1582d2 --- /dev/null +++ b/logic/settings/OverrideSetting.h @@ -0,0 +1,39 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#pragma once + +#include +#include + +#include "Setting.h" + +/*! + * \brief A setting that 'overrides another.' + * This means that the setting's default value will be the value of another setting. + * The other setting can be (and usually is) a part of a different SettingsObject + * than this one. + */ +class OverrideSetting : public Setting +{ + Q_OBJECT +public: + explicit OverrideSetting(std::shared_ptr other); + + virtual QVariant defValue() const; + +protected: + std::shared_ptr m_other; +}; diff --git a/logic/settings/Setting.cpp b/logic/settings/Setting.cpp new file mode 100644 index 00000000..5bdfe0fc --- /dev/null +++ b/logic/settings/Setting.cpp @@ -0,0 +1,53 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "Setting.h" +#include "logic/settings/SettingsObject.h" + +Setting::Setting(QStringList synonyms, QVariant defVal) + : QObject(), m_synonyms(synonyms), m_defVal(defVal) +{ +} + +QVariant Setting::get() const +{ + SettingsObject *sbase = m_storage; + if (!sbase) + { + return defValue(); + } + else + { + QVariant test = sbase->retrieveValue(*this); + if (!test.isValid()) + return defValue(); + return test; + } +} + +QVariant Setting::defValue() const +{ + return m_defVal; +} + +void Setting::set(QVariant value) +{ + emit SettingChanged(*this, value); +} + +void Setting::reset() +{ + emit settingReset(*this); +} diff --git a/logic/settings/Setting.h b/logic/settings/Setting.h new file mode 100644 index 00000000..406bdada --- /dev/null +++ b/logic/settings/Setting.h @@ -0,0 +1,117 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#pragma once + +#include +#include +#include +#include + +class SettingsObject; + +/*! + * + */ +class Setting : public QObject +{ + Q_OBJECT +public: + /** + * Construct a Setting + * + * Synonyms are all the possible names used in the settings object, in order of preference. + * First synonym is the ID, which identifies the setting in MultiMC. + * + * defVal is the default value that will be returned when the settings object + * doesn't have any value for this setting. + */ + explicit Setting(QStringList synonyms, QVariant defVal = QVariant()); + + /*! + * \brief Gets this setting's ID. + * This is used to refer to the setting within the application. + * \warning Changing the ID while the setting is registered with a SettingsObject results in + * undefined behavior. + * \return The ID of the setting. + */ + virtual QString id() const + { + return m_synonyms.first(); + } + + /*! + * \brief Gets this setting's config file key. + * This is used to store the setting's value in the config file. It is usually + * the same as the setting's ID, but it can be different. + * \return The setting's config file key. + */ + virtual QStringList configKeys() const + { + return m_synonyms; + } + + /*! + * \brief Gets this setting's value as a QVariant. + * This is done by calling the SettingsObject's retrieveValue() function. + * If this Setting doesn't have a SettingsObject, this returns an invalid QVariant. + * \return QVariant containing this setting's value. + * \sa value() + */ + virtual QVariant get() const; + + /*! + * \brief Gets this setting's default value. + * \return The default value of this setting. + */ + virtual QVariant defValue() const; + +signals: + /*! + * \brief Signal emitted when this Setting object's value changes. + * \param setting A reference to the Setting that changed. + * \param value This Setting object's new value. + */ + void SettingChanged(const Setting &setting, QVariant value); + + /*! + * \brief Signal emitted when this Setting object's value resets to default. + * \param setting A reference to the Setting that changed. + */ + void settingReset(const Setting &setting); + +public +slots: + /*! + * \brief Changes the setting's value. + * This is done by emitting the SettingChanged() signal which will then be + * handled by the SettingsObject object and cause the setting to change. + * \param value The new value. + */ + virtual void set(QVariant value); + + /*! + * \brief Reset the setting to default + * This is done by emitting the settingReset() signal which will then be + * handled by the SettingsObject object and cause the setting to change. + */ + virtual void reset(); + +protected: + friend class SettingsObject; + SettingsObject * m_storage; + QStringList m_synonyms; + QVariant m_defVal; +}; diff --git a/logic/settings/SettingsObject.cpp b/logic/settings/SettingsObject.cpp new file mode 100644 index 00000000..37f68251 --- /dev/null +++ b/logic/settings/SettingsObject.cpp @@ -0,0 +1,124 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "logic/settings/SettingsObject.h" +#include "logic/settings/Setting.h" +#include "logic/settings/OverrideSetting.h" +#include "logger/QsLog.h" + +#include + +SettingsObject::SettingsObject(QObject *parent) : QObject(parent) +{ +} + +SettingsObject::~SettingsObject() +{ + m_settings.clear(); +} + +std::shared_ptr SettingsObject::registerOverride(std::shared_ptr original) +{ + if (contains(original->id())) + { + QLOG_ERROR() << QString("Failed to register setting %1. ID already exists.") + .arg(original->id()); + return nullptr; // Fail + } + auto override = std::make_shared(original); + override->m_storage = this; + connectSignals(*override); + m_settings.insert(override->id(), override); + return override; +} + +std::shared_ptr SettingsObject::registerSetting(QStringList synonyms, QVariant defVal) +{ + if (synonyms.empty()) + return nullptr; + if (contains(synonyms.first())) + { + QLOG_ERROR() << QString("Failed to register setting %1. ID already exists.") + .arg(synonyms.first()); + return nullptr; // Fail + } + auto setting = std::make_shared(synonyms, defVal); + setting->m_storage = this; + connectSignals(*setting); + m_settings.insert(setting->id(), setting); + return setting; +} + +std::shared_ptr SettingsObject::getSetting(const QString &id) const +{ + // Make sure there is a setting with the given ID. + if (!m_settings.contains(id)) + return NULL; + + return m_settings[id]; +} + +QVariant SettingsObject::get(const QString &id) const +{ + auto setting = getSetting(id); + return (setting ? setting->get() : QVariant()); +} + +bool SettingsObject::set(const QString &id, QVariant value) +{ + auto setting = getSetting(id); + if (!setting) + { + QLOG_ERROR() << QString("Error changing setting %1. Setting doesn't exist.").arg(id); + return false; + } + else + { + setting->set(value); + return true; + } +} + +void SettingsObject::reset(const QString &id) const +{ + auto setting = getSetting(id); + if (setting) + setting->reset(); +} + +bool SettingsObject::contains(const QString &id) +{ + return m_settings.contains(id); +} + +bool SettingsObject::reload() +{ + for (auto setting : m_settings.values()) + { + setting->set(setting->get()); + } + return true; +} + +void SettingsObject::connectSignals(const Setting &setting) +{ + connect(&setting, SIGNAL(SettingChanged(const Setting &, QVariant)), + SLOT(changeSetting(const Setting &, QVariant))); + connect(&setting, SIGNAL(SettingChanged(const Setting &, QVariant)), + SIGNAL(SettingChanged(const Setting &, QVariant))); + + connect(&setting, SIGNAL(settingReset(Setting)), SLOT(resetSetting(const Setting &))); + connect(&setting, SIGNAL(settingReset(Setting)), SIGNAL(settingReset(const Setting &))); +} diff --git a/logic/settings/SettingsObject.h b/logic/settings/SettingsObject.h new file mode 100644 index 00000000..e46a1b7f --- /dev/null +++ b/logic/settings/SettingsObject.h @@ -0,0 +1,177 @@ +/* Copyright 2013 MultiMC Contributors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#pragma once + +#include +#include +#include +#include +#include + +class Setting; + +/*! + * \brief The SettingsObject handles communicating settings between the application and a + *settings file. + * The class keeps a list of Setting objects. Each Setting object represents one + * of the application's settings. These Setting objects are registered with + * a SettingsObject and can be managed similarly to the way a list works. + * + * \author Andrew Okin + * \date 2/22/2013 + * + * \sa Setting + */ +class SettingsObject : public QObject +{ + Q_OBJECT +public: + explicit SettingsObject(QObject *parent = 0); + virtual ~SettingsObject(); + /*! + * Registers an override setting for the given original setting in this settings object + * + * This will fail if there is already a setting with the same ID as + * the one that is being registered. + * \return A valid Setting shared pointer if successful. + */ + std::shared_ptr registerOverride(std::shared_ptr original); + + /*! + * Registers the given setting with this SettingsObject and connects the necessary signals. + * + * This will fail if there is already a setting with the same ID as + * the one that is being registered. + * \return A valid Setting shared pointer if successful. + */ + std::shared_ptr registerSetting(QStringList synonyms, + QVariant defVal = QVariant()); + + /*! + * Registers the given setting with this SettingsObject and connects the necessary signals. + * + * This will fail if there is already a setting with the same ID as + * the one that is being registered. + * \return A valid Setting shared pointer if successful. + */ + std::shared_ptr registerSetting(QString id, QVariant defVal = QVariant()) + { + return registerSetting(QStringList(id), defVal); + } + + /*! + * \brief Gets the setting with the given ID. + * \param id The ID of the setting to get. + * \return A pointer to the setting with the given ID. + * Returns null if there is no setting with the given ID. + * \sa operator []() + */ + std::shared_ptr getSetting(const QString &id) const; + + /*! + * \brief Gets the value of the setting with the given ID. + * \param id The ID of the setting to get. + * \return The setting's value as a QVariant. + * If no setting with the given ID exists, returns an invalid QVariant. + */ + QVariant get(const QString &id) const; + + /*! + * \brief Sets the value of the setting with the given ID. + * If no setting with the given ID exists, returns false and logs to qDebug + * \param id The ID of the setting to change. + * \param value The new value of the setting. + * \return True if successful, false if it failed. + */ + bool set(const QString &id, QVariant value); + + /*! + * \brief Reverts the setting with the given ID to default. + * \param id The ID of the setting to reset. + */ + void reset(const QString &id) const; + + /*! + * \brief Checks if this SettingsObject contains a setting with the given ID. + * \param id The ID to check for. + * \return True if the SettingsObject has a setting with the given ID. + */ + bool contains(const QString &id); + + /*! + * \brief Reloads the settings and emit signals for changed settings + * \return True if reloading was successful + */ + virtual bool reload(); + +signals: + /*! + * \brief Signal emitted when one of this SettingsObject object's settings changes. + * This is usually just connected directly to each Setting object's + * SettingChanged() signals. + * \param setting A reference to the Setting object that changed. + * \param value The Setting object's new value. + */ + void SettingChanged(const Setting &setting, QVariant value); + + /*! + * \brief Signal emitted when one of this SettingsObject object's settings resets. + * This is usually just connected directly to each Setting object's + * settingReset() signals. + * \param setting A reference to the Setting object that changed. + */ + void settingReset(const Setting &setting); + +protected +slots: + /*! + * \brief Changes a setting. + * This slot is usually connected to each Setting object's + * SettingChanged() signal. The signal is emitted, causing this slot + * to update the setting's value in the config file. + * \param setting A reference to the Setting object that changed. + * \param value The setting's new value. + */ + virtual void changeSetting(const Setting &setting, QVariant value) = 0; + + /*! + * \brief Resets a setting. + * This slot is usually connected to each Setting object's + * settingReset() signal. The signal is emitted, causing this slot + * to update the setting's value in the config file. + * \param setting A reference to the Setting object that changed. + */ + virtual void resetSetting(const Setting &setting) = 0; + +protected: + /*! + * \brief Connects the necessary signals to the given Setting. + * \param setting The setting to connect. + */ + void connectSignals(const Setting &setting); + + /*! + * \brief Function used by Setting objects to get their values from the SettingsObject. + * \param setting The + * \return + */ + virtual QVariant retrieveValue(const Setting &setting) = 0; + + friend class Setting; + +private: + QMap> m_settings; +}; diff --git a/logic/tools/JProfiler.cpp b/logic/tools/JProfiler.cpp index 35d5d304..988a875a 100644 --- a/logic/tools/JProfiler.cpp +++ b/logic/tools/JProfiler.cpp @@ -3,7 +3,7 @@ #include #include -#include "settingsobject.h" +#include "logic/settings/SettingsObject.h" #include "logic/MinecraftProcess.h" #include "logic/BaseInstance.h" #include "MultiMC.h" diff --git a/logic/tools/JVisualVM.cpp b/logic/tools/JVisualVM.cpp index 02e7d8b5..09ab1762 100644 --- a/logic/tools/JVisualVM.cpp +++ b/logic/tools/JVisualVM.cpp @@ -3,7 +3,7 @@ #include #include -#include "settingsobject.h" +#include "logic/settings/SettingsObject.h" #include "logic/MinecraftProcess.h" #include "logic/BaseInstance.h" #include "MultiMC.h" diff --git a/logic/tools/MCEditTool.cpp b/logic/tools/MCEditTool.cpp index 36b8d5bd..91643585 100644 --- a/logic/tools/MCEditTool.cpp +++ b/logic/tools/MCEditTool.cpp @@ -5,7 +5,7 @@ #include #include -#include "settingsobject.h" +#include "logic/settings/SettingsObject.h" #include "logic/BaseInstance.h" #include "MultiMC.h" diff --git a/logic/updater/UpdateChecker.cpp b/logic/updater/UpdateChecker.cpp index e47e1c4c..c2895430 100644 --- a/logic/updater/UpdateChecker.cpp +++ b/logic/updater/UpdateChecker.cpp @@ -24,7 +24,7 @@ #include #include -#include +#include "logic/settings/SettingsObject.h" #define API_VERSION 0 #define CHANLIST_FORMAT 0 diff --git a/tests/tst_UpdateChecker.cpp b/tests/tst_UpdateChecker.cpp index ae6fc193..8351ad75 100644 --- a/tests/tst_UpdateChecker.cpp +++ b/tests/tst_UpdateChecker.cpp @@ -1,8 +1,8 @@ #include #include -#include "depends/settings/settingsobject.h" -#include "depends/settings/setting.h" +#include "logic/settings/SettingsObject.h" +#include "logic/settings/Setting.h" #include "BuildConfig.h" #include "TestUtil.h" diff --git a/tests/tst_inifile.cpp b/tests/tst_inifile.cpp index c0f57c12..93930ae9 100644 --- a/tests/tst_inifile.cpp +++ b/tests/tst_inifile.cpp @@ -1,7 +1,7 @@ #include #include "TestUtil.h" -#include "depends/settings/inifile.h" +#include "logic/settings/INIFile.h" class IniFileTest : public QObject { -- cgit v1.2.3