diff --git a/chatterino.pro b/chatterino.pro index 46ae571cb..fa4f35fed 100644 --- a/chatterino.pro +++ b/chatterino.pro @@ -18,6 +18,8 @@ PRECOMPILED_HEADER = src/PrecompiledHeader.hpp CONFIG += precompile_header DEFINES += CHATTERINO DEFINES += "AB_NAMESPACE=chatterino" +DEFINES += AB_CUSTOM_THEME +DEFINES += AB_CUSTOM_SETTINGS CONFIG += AB_NOT_STANDALONE useBreakpad { @@ -139,7 +141,6 @@ SOURCES += \ src/widgets/helper/ScrollbarHighlight.cpp \ src/widgets/helper/SearchPopup.cpp \ src/widgets/helper/SettingsDialogTab.cpp \ - src/widgets/helper/SignalLabel.cpp \ src/widgets/Notebook.cpp \ src/widgets/Scrollbar.cpp \ src/widgets/settingspages/AboutPage.cpp \ @@ -195,7 +196,6 @@ SOURCES += \ src/RunGui.cpp \ src/BrowserExtension.cpp \ src/util/FormatTime.cpp \ - src/util/FunctionEventFilter.cpp \ src/controllers/notifications/NotificationModel.cpp \ src/singletons/Toasts.cpp \ src/common/DownloadManager.cpp \ @@ -282,7 +282,6 @@ HEADERS += \ src/singletons/helper/LoggingChannel.hpp \ src/controllers/moderationactions/ModerationAction.hpp \ src/singletons/WindowManager.hpp \ - src/util/Clamp.hpp \ src/util/CombinePath.hpp \ src/util/ConcurrentMap.hpp \ src/util/DebugCount.hpp \ @@ -320,7 +319,6 @@ HEADERS += \ src/widgets/helper/ScrollbarHighlight.hpp \ src/widgets/helper/SearchPopup.hpp \ src/widgets/helper/SettingsDialogTab.hpp \ - src/widgets/helper/SignalLabel.hpp \ src/widgets/Notebook.hpp \ src/widgets/Scrollbar.hpp \ src/widgets/settingspages/AboutPage.hpp \ @@ -382,7 +380,6 @@ HEADERS += \ src/RunGui.hpp \ src/BrowserExtension.hpp \ src/util/FormatTime.hpp \ - src/util/FunctionEventFilter.hpp \ src/controllers/notifications/NotificationModel.hpp \ src/singletons/Toasts.hpp \ src/common/DownloadManager.hpp \ diff --git a/lib/appbase b/lib/appbase index 57d61602c..a830d3692 160000 --- a/lib/appbase +++ b/lib/appbase @@ -1 +1 @@ -Subproject commit 57d61602c375cc83418ba59a36535247060dab6a +Subproject commit a830d3692bdbe53b79f244cf1d4695e2a49fb7ed diff --git a/src/main.cpp b/src/main.cpp index 52049b0c2..6cce245e2 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -27,7 +27,7 @@ int main(int argc, char **argv) else { Paths paths; - Settings settings(paths); + Settings settings(paths.settingsDirectory); runGui(a, paths, settings); } diff --git a/src/singletons/Settings.cpp b/src/singletons/Settings.cpp index 03b58936d..db300ae8e 100644 --- a/src/singletons/Settings.cpp +++ b/src/singletons/Settings.cpp @@ -8,31 +8,12 @@ namespace chatterino { -std::vector> _settings; - Settings *Settings::instance = nullptr; -void _actuallyRegisterSetting( - std::weak_ptr setting) -{ - _settings.push_back(setting); -} - -Settings::Settings(Paths &paths) +Settings::Settings(const QString &settingsDirectory) + : ABSettings(settingsDirectory) { instance = this; - - QString settingsPath = paths.settingsDirectory + "/settings.json"; - - // get global instance of the settings library - auto settingsInstance = pajlada::Settings::SettingManager::getInstance(); - - settingsInstance->load(qPrintable(settingsPath)); - - settingsInstance->setBackupEnabled(true); - settingsInstance->setBackupSlots(9); - settingsInstance->saveMethod = - pajlada::Settings::SettingManager::SaveMethod::SaveOnExit; } Settings &Settings::getInstance() @@ -40,69 +21,6 @@ Settings &Settings::getInstance() return *instance; } -void Settings::saveSnapshot() -{ - rapidjson::Document *d = new rapidjson::Document(rapidjson::kObjectType); - rapidjson::Document::AllocatorType &a = d->GetAllocator(); - - for (const auto &weakSetting : _settings) - { - auto setting = weakSetting.lock(); - if (!setting) - { - continue; - } - - rapidjson::Value key(setting->getPath().c_str(), a); - auto curVal = setting->unmarshalJSON(); - if (curVal == nullptr) - { - continue; - } - - rapidjson::Value val; - val.CopyFrom(*curVal, a); - d->AddMember(key.Move(), val.Move(), a); - } - - // log("Snapshot state: {}", rj::stringify(*d)); - - this->snapshot_.reset(d); -} - -void Settings::restoreSnapshot() -{ - if (!this->snapshot_) - { - return; - } - - const auto &snapshot = *(this->snapshot_.get()); - - if (!snapshot.IsObject()) - { - return; - } - - for (const auto &weakSetting : _settings) - { - auto setting = weakSetting.lock(); - if (!setting) - { - continue; - } - - const char *path = setting->getPath().c_str(); - - if (!snapshot.HasMember(path)) - { - continue; - } - - setting->marshalJSON(snapshot[path]); - } -} - Settings *getSettings() { return &Settings::getInstance(); diff --git a/src/singletons/Settings.hpp b/src/singletons/Settings.hpp index e23bf6a72..4a807b509 100644 --- a/src/singletons/Settings.hpp +++ b/src/singletons/Settings.hpp @@ -1,8 +1,7 @@ #pragma once -#include "Paths.hpp" +#include "ABSettings.hpp" -#include "common/ChatterinoSetting.hpp" #include "controllers/highlights/HighlightPhrase.hpp" #include "controllers/moderationactions/ModerationAction.hpp" @@ -11,15 +10,12 @@ namespace chatterino { -void _actuallyRegisterSetting( - std::weak_ptr setting); - -class Settings +class Settings : public ABSettings { static Settings *instance; public: - Settings(Paths &paths); + Settings(const QString &settingsDirectory); static Settings &getInstance(); @@ -50,9 +46,7 @@ public: "/appearance/messages/collapseMessagesMinLines", 0}; BoolSetting alternateMessages = { "/appearance/messages/alternateMessageBackground", false}; - IntSetting uiScale = {"/appearance/uiScale", 0}; IntSetting boldScale = {"/appearance/boldScale", 57}; - BoolSetting windowTopMost = {"/appearance/windowAlwaysOnTop", false}; BoolSetting showTabCloseButton = {"/appearance/showTabCloseButton", true}; BoolSetting showTabLive = {"/appearance/showTabLiveButton", false}; BoolSetting hidePreferencesButton = {"/appearance/hidePreferencesButton", @@ -194,15 +188,8 @@ public: QStringSetting cachePath = {"/cache/path", ""}; - void saveSnapshot(); - void restoreSnapshot(); - private: void updateModerationActions(); - - std::unique_ptr snapshot_; }; -Settings *getSettings(); - } // namespace chatterino diff --git a/src/singletons/Theme.cpp b/src/singletons/Theme.cpp index f209c2d0f..5717026ce 100644 --- a/src/singletons/Theme.cpp +++ b/src/singletons/Theme.cpp @@ -1,6 +1,7 @@ #define LOOKUP_COLOR_COUNT 360 #include "singletons/Theme.hpp" +#include "Application.hpp" #include @@ -8,36 +9,6 @@ namespace chatterino { -namespace detail { - - double getMultiplierByTheme(const QString &themeName) - { - if (themeName == "Light") - { - return 0.8; - } - else if (themeName == "White") - { - return 1.0; - } - else if (themeName == "Black") - { - return -1.0; - } - else if (themeName == "Dark") - { - return -0.8; - } - else if (themeName == "Custom") - { - return getSettings()->customThemeMultiplier.getValue(); - } - - return -0.8; - } - -} // namespace detail - Theme::Theme() { this->update(); @@ -46,134 +17,21 @@ Theme::Theme() this->themeHue.connectSimple([this](auto) { this->update(); }, false); } -void Theme::update() -{ - this->actuallyUpdate(this->themeHue, detail::getMultiplierByTheme( - this->themeName.getValue())); -} - // hue: theme color (0 - 1) // multiplier: 1 = white, 0.8 = light, -0.8 dark, -1 black void Theme::actuallyUpdate(double hue, double multiplier) { - isLight_ = multiplier > 0; - bool lightWin = isLight_; - - // QColor themeColor = QColor::fromHslF(hue, 0.43, 0.5); - QColor themeColor = QColor::fromHslF(hue, 0.8, 0.5); - QColor themeColorNoSat = QColor::fromHslF(hue, 0, 0.5); - - qreal sat = 0; - // 0.05; + ABTheme::actuallyUpdate(hue, multiplier); auto getColor = [multiplier](double h, double s, double l, double a = 1.0) { return QColor::fromHslF(h, s, ((l - 0.5) * multiplier) + 0.5, a); }; - /// WINDOW - { - QColor bg = -#ifdef Q_OS_LINUX - this->window.background = lightWin ? "#fff" : QColor(61, 60, 56); -#else - this->window.background = lightWin ? "#fff" : "#111"; -#endif + auto sat = qreal(0); + auto isLight_ = this->isLightTheme(); + auto flat = isLight_; - QColor fg = this->window.text = lightWin ? "#000" : "#eee"; - this->window.borderFocused = lightWin ? "#ccc" : themeColor; - this->window.borderUnfocused = lightWin ? "#ccc" : themeColorNoSat; - - // Ubuntu style - // TODO: add setting for this - // TabText = QColor(210, 210, 210); - // TabBackground = QColor(61, 60, 56); - // TabHoverText = QColor(210, 210, 210); - // TabHoverBackground = QColor(73, 72, 68); - - // message (referenced later) - this->messages.textColors.caret = // - this->messages.textColors.regular = isLight_ ? "#000" : "#fff"; - - QColor highlighted = lightWin ? QColor("#ff0000") : QColor("#ee6166"); - - /// TABS - if (lightWin) - { - this->tabs.regular = { - QColor("#444"), - {QColor("#fff"), QColor("#eee"), QColor("#fff")}, - {QColor("#fff"), QColor("#fff"), QColor("#fff")}}; - this->tabs.newMessage = { - QColor("#222"), - {QColor("#fff"), QColor("#eee"), QColor("#fff")}, - {QColor("#bbb"), QColor("#bbb"), QColor("#bbb")}}; - this->tabs.highlighted = { - fg, - {QColor("#fff"), QColor("#eee"), QColor("#fff")}, - {highlighted, highlighted, highlighted}}; - this->tabs.selected = { - QColor("#000"), - {QColor("#b4d7ff"), QColor("#b4d7ff"), QColor("#b4d7ff")}, - {QColor("#00aeef"), QColor("#00aeef"), QColor("#00aeef")}}; - } - else - { - this->tabs.regular = { - QColor("#aaa"), - {QColor("#252525"), QColor("#252525"), QColor("#252525")}, - {QColor("#444"), QColor("#444"), QColor("#444")}}; - this->tabs.newMessage = { - fg, - {QColor("#252525"), QColor("#252525"), QColor("#252525")}, - {QColor("#888"), QColor("#888"), QColor("#888")}}; - this->tabs.highlighted = { - fg, - {QColor("#252525"), QColor("#252525"), QColor("#252525")}, - {highlighted, highlighted, highlighted}}; - - this->tabs.selected = { - QColor("#fff"), - {QColor("#555555"), QColor("#555555"), QColor("#555555")}, - {QColor("#00aeef"), QColor("#00aeef"), QColor("#00aeef")}}; - } - - this->splits.input.focusedLine = highlighted; - - // scrollbar - this->scrollbars.highlights.highlight = QColor("#ee6166"); - this->scrollbars.highlights.subscription = QColor("#C466FF"); - - // this->tabs.newMessage = { - // fg, - // {QBrush(blendColors(themeColor, "#ccc", 0.9), Qt::FDiagPattern), - // QBrush(blendColors(themeColor, "#ccc", 0.9), Qt::FDiagPattern), - // QBrush(blendColors(themeColorNoSat, "#ccc", 0.9), - // Qt::FDiagPattern)}}; - - // this->tabs.newMessage = { - // fg, - // {QBrush(blendColors(themeColor, "#666", 0.7), - // Qt::FDiagPattern), - // QBrush(blendColors(themeColor, "#666", 0.5), - // Qt::FDiagPattern), - // QBrush(blendColors(themeColorNoSat, "#666", 0.7), - // Qt::FDiagPattern)}}; - // this->tabs.highlighted = {fg, {QColor("#777"), - // QColor("#777"), QColor("#666")}}; - - this->tabs.bottomLine = this->tabs.selected.backgrounds.regular.color(); - } // namespace chatterino - - // Split - bool flat = isLight_; - - this->splits.messageSeperator = - isLight_ ? QColor(127, 127, 127) : QColor(60, 60, 60); - this->splits.background = getColor(0, sat, 1); - this->splits.dropPreview = QColor(0, 148, 255, 0x30); - this->splits.dropPreviewBorder = QColor(0, 148, 255, 0xff); - - if (isLight_) + if (this->isLightTheme()) { this->splits.dropTargetRect = QColor(255, 255, 255, 0x00); this->splits.dropTargetRectBorder = QColor(0, 148, 255, 0x00); @@ -207,65 +65,18 @@ void Theme::actuallyUpdate(double hue, double multiplier) (isLight_ ? "#68B1FF" : this->tabs.selected.backgrounds.regular.color().name()); - // Message - this->messages.textColors.link = - isLight_ ? QColor(66, 134, 244) : QColor(66, 134, 244); - this->messages.textColors.system = QColor(140, 127, 127); + this->splits.input.focusedLine = this->tabs.highlighted.line.regular; - this->messages.backgrounds.regular = splits.background; - this->messages.backgrounds.alternate = getColor(0, sat, 0.96); - - if (isLight_) - { - this->messages.backgrounds.highlighted = - blendColors(themeColor, this->messages.backgrounds.regular, 0.8); - } - else - { - this->messages.backgrounds.highlighted = - QColor(getSettings()->highlightColor); - } - - this->messages.backgrounds.subscription = - blendColors(QColor("#C466FF"), this->messages.backgrounds.regular, 0.7); - - // this->messages.backgrounds.resub - // this->messages.backgrounds.whisper - this->messages.disabled = getColor(0, sat, 1, 0.6); - // this->messages.seperator = - // this->messages.seperatorInner = - - // Scrollbar - this->scrollbars.background = QColor(0, 0, 0, 0); - // this->scrollbars.background = splits.background; - // this->scrollbars.background.setAlphaF(qreal(0.2)); - this->scrollbars.thumb = getColor(0, sat, 0.70); - this->scrollbars.thumbSelected = getColor(0, sat, 0.65); - - // tooltip - this->tooltip.background = QColor(0, 0, 0); - this->tooltip.text = QColor(255, 255, 255); - - // Selection - this->messages.selection = - isLightTheme() ? QColor(0, 0, 0, 64) : QColor(255, 255, 255, 64); - - this->updated.invoke(); -} // namespace chatterino - -QColor Theme::blendColors(const QColor &color1, const QColor &color2, - qreal ratio) -{ - int r = int(color1.red() * (1 - ratio) + color2.red() * ratio); - int g = int(color1.green() * (1 - ratio) + color2.green() * ratio); - int b = int(color1.blue() * (1 - ratio) + color2.blue() * ratio); - - return QColor(r, g, b, 255); + this->splits.messageSeperator = + isLight_ ? QColor(127, 127, 127) : QColor(60, 60, 60); + this->splits.background = getColor(0, sat, 1); + this->splits.dropPreview = QColor(0, 148, 255, 0x30); + this->splits.dropPreviewBorder = QColor(0, 148, 255, 0xff); } void Theme::normalizeColor(QColor &color) { - if (this->isLight_) + if (this->isLightTheme()) { if (color.lightnessF() > 0.5) { @@ -300,4 +111,9 @@ void Theme::normalizeColor(QColor &color) } } +Theme *getTheme() +{ + return getApp()->themes; +} + } // namespace chatterino diff --git a/src/singletons/Theme.hpp b/src/singletons/Theme.hpp index 80f500838..decbb1d47 100644 --- a/src/singletons/Theme.hpp +++ b/src/singletons/Theme.hpp @@ -1,5 +1,6 @@ #pragma once +#include "ABTheme.hpp" #include "common/Singleton.hpp" #include "util/RapidJsonSerializeQString.hpp" @@ -12,48 +13,11 @@ namespace chatterino { class WindowManager; -class Theme final : public Singleton +class Theme final : public Singleton, public ABTheme { public: Theme(); - bool isLightTheme() const - { - return this->isLight_; - } - - struct TabColors { - QColor text; - struct { - QBrush regular; - QBrush hover; - QBrush unfocused; - } backgrounds; - struct { - QColor regular; - QColor hover; - QColor unfocused; - } line; - }; - - /// WINDOW - struct { - QColor background; - QColor text; - QColor borderUnfocused; - QColor borderFocused; - } window; - - /// TABS - struct { - TabColors regular; - TabColors newMessage; - TabColors highlighted; - TabColors selected; - QColor border; - QColor bottomLine; - } tabs; - /// SPLITS struct { QColor messageSeperator; @@ -84,66 +48,16 @@ public: } input; } splits; - /// MESSAGES - struct { - struct { - QColor regular; - QColor caret; - QColor link; - QColor system; - } textColors; - - struct { - QColor regular; - QColor alternate; - QColor highlighted; - QColor subscription; - // QColor whisper; - } backgrounds; - - QColor disabled; - // QColor seperator; - // QColor seperatorInner; - QColor selection; - } messages; - - /// SCROLLBAR - struct { - QColor background; - QColor thumb; - QColor thumbSelected; - struct { - QColor highlight; - QColor subscription; - } highlights; - } scrollbars; - - /// TOOLTIP - struct { - QColor text; - QColor background; - } tooltip; - void normalizeColor(QColor &color); - void update(); - - pajlada::Signals::NoArgSignal updated; - - QStringSetting themeName{"/appearance/theme/name", "Dark"}; - DoubleSetting themeHue{"/appearance/theme/hue", 0.0}; - private: - void actuallyUpdate(double hue, double multiplier); - QColor blendColors(const QColor &color1, const QColor &color2, qreal ratio); + void actuallyUpdate(double hue, double multiplier) override; void fillLookupTableValues(double (&array)[360], double from, double to, double fromValue, double toValue); double middleLookupTable_[360] = {}; double minLookupTable_[360] = {}; - bool isLight_ = false; - pajlada::Signals::NoArgSignal repaintVisibleChatWidgets_; friend class WindowManager; diff --git a/src/singletons/Toasts.cpp b/src/singletons/Toasts.cpp index 36f46d7ad..367724368 100644 --- a/src/singletons/Toasts.cpp +++ b/src/singletons/Toasts.cpp @@ -7,6 +7,7 @@ #include "providers/twitch/TwitchChannel.hpp" #include "providers/twitch/TwitchCommon.hpp" #include "providers/twitch/TwitchServer.hpp" +#include "singletons/Paths.hpp" #ifdef Q_OS_WIN diff --git a/src/util/Clamp.hpp b/src/util/Clamp.hpp deleted file mode 100644 index 5a3e46e72..000000000 --- a/src/util/Clamp.hpp +++ /dev/null @@ -1,13 +0,0 @@ -#pragma once - -namespace chatterino { - -// http://en.cppreference.com/w/cpp/algorithm/clamp - -template -constexpr const T &clamp(const T &v, const T &lo, const T &hi) -{ - return assert(!(hi < lo)), (v < lo) ? lo : (hi < v) ? hi : v; -} - -} // namespace chatterino diff --git a/src/util/FunctionEventFilter.cpp b/src/util/FunctionEventFilter.cpp deleted file mode 100644 index 3006597b2..000000000 --- a/src/util/FunctionEventFilter.cpp +++ /dev/null @@ -1,17 +0,0 @@ -#include "FunctionEventFilter.hpp" - -namespace chatterino { - -FunctionEventFilter::FunctionEventFilter( - QObject *parent, std::function function) - : QObject(parent) - , function_(std::move(function)) -{ -} - -bool FunctionEventFilter::eventFilter(QObject *watched, QEvent *event) -{ - return this->function_(watched, event); -} - -} // namespace chatterino diff --git a/src/util/FunctionEventFilter.hpp b/src/util/FunctionEventFilter.hpp deleted file mode 100644 index a849af6f0..000000000 --- a/src/util/FunctionEventFilter.hpp +++ /dev/null @@ -1,24 +0,0 @@ -#pragma once - -#include -#include -#include - -namespace chatterino { - -class FunctionEventFilter : public QObject -{ - Q_OBJECT - -public: - FunctionEventFilter(QObject *parent, - std::function function); - -protected: - bool eventFilter(QObject *watched, QEvent *event) override; - -private: - std::function function_; -}; - -} // namespace chatterino diff --git a/src/widgets/helper/SignalLabel.cpp b/src/widgets/helper/SignalLabel.cpp deleted file mode 100644 index 46fd0d80c..000000000 --- a/src/widgets/helper/SignalLabel.cpp +++ /dev/null @@ -1,41 +0,0 @@ -#include "widgets/helper/SignalLabel.hpp" - -namespace chatterino { - -SignalLabel::SignalLabel(QWidget *parent, Qt::WindowFlags f) - : QLabel(parent, f) -{ -} - -void SignalLabel::mouseDoubleClickEvent(QMouseEvent *ev) -{ - emit this->mouseDoubleClick(ev); -} - -void SignalLabel::mousePressEvent(QMouseEvent *event) -{ - if (event->button() == Qt::LeftButton) - { - emit mouseDown(); - } - - event->ignore(); -} - -void SignalLabel::mouseReleaseEvent(QMouseEvent *event) -{ - if (event->button() == Qt::LeftButton) - { - emit mouseUp(); - } - - event->ignore(); -} - -void SignalLabel::mouseMoveEvent(QMouseEvent *event) -{ - emit this->mouseMove(event); - event->ignore(); -} - -} // namespace chatterino diff --git a/src/widgets/helper/SignalLabel.hpp b/src/widgets/helper/SignalLabel.hpp deleted file mode 100644 index 382840265..000000000 --- a/src/widgets/helper/SignalLabel.hpp +++ /dev/null @@ -1,32 +0,0 @@ -#pragma once - -#include -#include -#include -#include - -namespace chatterino { - -class SignalLabel : public QLabel -{ - Q_OBJECT - -public: - explicit SignalLabel(QWidget *parent = nullptr, Qt::WindowFlags f = 0); - virtual ~SignalLabel() override = default; - -signals: - void mouseDoubleClick(QMouseEvent *ev); - - void mouseDown(); - void mouseUp(); - void mouseMove(QMouseEvent *event); - -protected: - void mouseDoubleClickEvent(QMouseEvent *ev) override; - void mousePressEvent(QMouseEvent *event) override; - void mouseReleaseEvent(QMouseEvent *event) override; - void mouseMoveEvent(QMouseEvent *event) override; -}; - -} // namespace chatterino diff --git a/src/widgets/settingspages/GeneralPage.cpp b/src/widgets/settingspages/GeneralPage.cpp index 78ad6d804..80b70c8db 100644 --- a/src/widgets/settingspages/GeneralPage.cpp +++ b/src/widgets/settingspages/GeneralPage.cpp @@ -6,6 +6,7 @@ #include "Application.hpp" #include "singletons/Fonts.hpp" +#include "singletons/Paths.hpp" #include "singletons/Theme.hpp" #include "singletons/WindowManager.hpp" #include "util/FuzzyConvert.hpp"