Merge pull request #12272 from AdmiralCurtiss/dark-mode-gui
DolphinQt: Allow forcing light or dark style on Windows.
This commit is contained in:
commit
1748e6416f
|
@ -133,7 +133,7 @@ void BalloonTip::UpdateBoundsAndRedraw(const QPoint& pos, ShowArrow show_arrow)
|
||||||
const QRect screen_rect = screen->geometry();
|
const QRect screen_rect = screen->geometry();
|
||||||
|
|
||||||
QSize sh = sizeHint();
|
QSize sh = sizeHint();
|
||||||
// The look should resemble the default tooltip style set in Settings::SetCurrentUserStyle()
|
// The look should resemble the default tooltip style set in Settings::ApplyStyle()
|
||||||
const int border = 1;
|
const int border = 1;
|
||||||
const int arrow_height = 18;
|
const int arrow_height = 18;
|
||||||
const int arrow_width = 18;
|
const int arrow_width = 18;
|
||||||
|
|
|
@ -247,7 +247,7 @@ int main(int argc, char* argv[])
|
||||||
|
|
||||||
Settings::Instance().InitDefaultPalette();
|
Settings::Instance().InitDefaultPalette();
|
||||||
Settings::Instance().UpdateSystemDark();
|
Settings::Instance().UpdateSystemDark();
|
||||||
Settings::Instance().SetCurrentUserStyle(Settings::Instance().GetCurrentUserStyle());
|
Settings::Instance().ApplyStyle();
|
||||||
|
|
||||||
MainWindow win{std::move(boot), static_cast<const char*>(options.get("movie"))};
|
MainWindow win{std::move(boot), static_cast<const char*>(options.get("movie"))};
|
||||||
win.Show();
|
win.Show();
|
||||||
|
|
|
@ -240,9 +240,7 @@ MainWindow::MainWindow(std::unique_ptr<BootParameters> boot_parameters,
|
||||||
|
|
||||||
#if QT_VERSION >= QT_VERSION_CHECK(6, 5, 0)
|
#if QT_VERSION >= QT_VERSION_CHECK(6, 5, 0)
|
||||||
connect(QGuiApplication::styleHints(), &QStyleHints::colorSchemeChanged, this,
|
connect(QGuiApplication::styleHints(), &QStyleHints::colorSchemeChanged, this,
|
||||||
[](Qt::ColorScheme colorScheme) {
|
[](Qt::ColorScheme colorScheme) { Settings::Instance().ApplyStyle(); });
|
||||||
Settings::Instance().SetCurrentUserStyle(Settings::Instance().GetCurrentUserStyle());
|
|
||||||
});
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
connect(m_cheats_manager, &CheatsManager::OpenGeneralSettings, this,
|
connect(m_cheats_manager, &CheatsManager::OpenGeneralSettings, this,
|
||||||
|
@ -1739,7 +1737,7 @@ bool MainWindow::nativeEvent(const QByteArray& eventType, void* message, qintptr
|
||||||
settings.UpdateSystemDark();
|
settings.UpdateSystemDark();
|
||||||
if (settings.IsSystemDark() != was_dark_before)
|
if (settings.IsSystemDark() != was_dark_before)
|
||||||
{
|
{
|
||||||
settings.SetCurrentUserStyle(settings.GetCurrentUserStyle());
|
settings.ApplyStyle();
|
||||||
|
|
||||||
// force the colors in the Skylander window to update
|
// force the colors in the Skylander window to update
|
||||||
if (m_skylander_window)
|
if (m_skylander_window)
|
||||||
|
|
|
@ -14,7 +14,7 @@
|
||||||
void SetQWidgetWindowDecorations(QWidget* widget)
|
void SetQWidgetWindowDecorations(QWidget* widget)
|
||||||
{
|
{
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
if (!Settings::Instance().IsSystemDark())
|
if (!Settings::Instance().IsThemeDark())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
BOOL use_dark_title_bar = TRUE;
|
BOOL use_dark_title_bar = TRUE;
|
||||||
|
|
|
@ -123,7 +123,7 @@ void Settings::SetThemeName(const QString& theme_name)
|
||||||
emit ThemeChanged();
|
emit ThemeChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
QString Settings::GetCurrentUserStyle() const
|
QString Settings::GetUserStyleName() const
|
||||||
{
|
{
|
||||||
if (GetQSettings().contains(QStringLiteral("userstyle/name")))
|
if (GetQSettings().contains(QStringLiteral("userstyle/name")))
|
||||||
return GetQSettings().value(QStringLiteral("userstyle/name")).toString();
|
return GetQSettings().value(QStringLiteral("userstyle/name")).toString();
|
||||||
|
@ -132,6 +132,11 @@ QString Settings::GetCurrentUserStyle() const
|
||||||
return QFileInfo(GetQSettings().value(QStringLiteral("userstyle/path")).toString()).fileName();
|
return QFileInfo(GetQSettings().value(QStringLiteral("userstyle/path")).toString()).fileName();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Settings::SetUserStyleName(const QString& stylesheet_name)
|
||||||
|
{
|
||||||
|
GetQSettings().setValue(QStringLiteral("userstyle/name"), stylesheet_name);
|
||||||
|
}
|
||||||
|
|
||||||
void Settings::InitDefaultPalette()
|
void Settings::InitDefaultPalette()
|
||||||
{
|
{
|
||||||
s_default_palette = std::make_unique<QPalette>(qApp->palette());
|
s_default_palette = std::make_unique<QPalette>(qApp->palette());
|
||||||
|
@ -169,12 +174,14 @@ bool Settings::IsThemeDark()
|
||||||
}
|
}
|
||||||
|
|
||||||
// Calling this before the main window has been created breaks the style of some widgets.
|
// Calling this before the main window has been created breaks the style of some widgets.
|
||||||
void Settings::SetCurrentUserStyle(const QString& stylesheet_name)
|
void Settings::ApplyStyle()
|
||||||
{
|
{
|
||||||
|
const StyleType style_type = GetStyleType();
|
||||||
|
const QString stylesheet_name = GetUserStyleName();
|
||||||
QString stylesheet_contents;
|
QString stylesheet_contents;
|
||||||
|
|
||||||
// If we haven't found one, we continue with an empty (default) style
|
// If we haven't found one, we continue with an empty (default) style
|
||||||
if (!stylesheet_name.isEmpty() && AreUserStylesEnabled())
|
if (!stylesheet_name.isEmpty() && style_type == StyleType::User)
|
||||||
{
|
{
|
||||||
// Load custom user stylesheet
|
// Load custom user stylesheet
|
||||||
QDir directory = QDir(QString::fromStdString(File::GetUserPath(D_STYLES_IDX)));
|
QDir directory = QDir(QString::fromStdString(File::GetUserPath(D_STYLES_IDX)));
|
||||||
|
@ -191,7 +198,7 @@ void Settings::SetCurrentUserStyle(const QString& stylesheet_name)
|
||||||
// which would select Qt's default theme, but unlike other OSes we don't automatically get a
|
// which would select Qt's default theme, but unlike other OSes we don't automatically get a
|
||||||
// default dark theme on Windows when the user has selected dark mode in the Windows settings.
|
// default dark theme on Windows when the user has selected dark mode in the Windows settings.
|
||||||
// So manually check if the user wants dark mode and, if yes, load our embedded dark theme.
|
// So manually check if the user wants dark mode and, if yes, load our embedded dark theme.
|
||||||
if (IsSystemDark())
|
if (style_type == StyleType::Dark || (style_type != StyleType::Light && IsSystemDark()))
|
||||||
{
|
{
|
||||||
QFile file(QStringLiteral(":/dolphin_dark_win/dark.qss"));
|
QFile file(QStringLiteral(":/dolphin_dark_win/dark.qss"));
|
||||||
if (file.open(QFile::ReadOnly))
|
if (file.open(QFile::ReadOnly))
|
||||||
|
@ -243,18 +250,32 @@ void Settings::SetCurrentUserStyle(const QString& stylesheet_name)
|
||||||
}
|
}
|
||||||
|
|
||||||
qApp->setStyleSheet(stylesheet_contents);
|
qApp->setStyleSheet(stylesheet_contents);
|
||||||
|
|
||||||
GetQSettings().setValue(QStringLiteral("userstyle/name"), stylesheet_name);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Settings::AreUserStylesEnabled() const
|
Settings::StyleType Settings::GetStyleType() const
|
||||||
{
|
{
|
||||||
return GetQSettings().value(QStringLiteral("userstyle/enabled"), false).toBool();
|
if (GetQSettings().contains(QStringLiteral("userstyle/styletype")))
|
||||||
|
{
|
||||||
|
bool ok = false;
|
||||||
|
const int type_int = GetQSettings().value(QStringLiteral("userstyle/styletype")).toInt(&ok);
|
||||||
|
if (ok && type_int >= static_cast<int>(StyleType::MinValue) &&
|
||||||
|
type_int <= static_cast<int>(StyleType::MaxValue))
|
||||||
|
{
|
||||||
|
return static_cast<StyleType>(type_int);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// if the style type is unset or invalid, try the old enabled flag instead
|
||||||
|
const bool enabled = GetQSettings().value(QStringLiteral("userstyle/enabled"), false).toBool();
|
||||||
|
return enabled ? StyleType::User : StyleType::System;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Settings::SetUserStylesEnabled(bool enabled)
|
void Settings::SetStyleType(StyleType type)
|
||||||
{
|
{
|
||||||
GetQSettings().setValue(QStringLiteral("userstyle/enabled"), enabled);
|
GetQSettings().setValue(QStringLiteral("userstyle/styletype"), static_cast<int>(type));
|
||||||
|
|
||||||
|
// also set the old setting so that the config is correctly intepreted by older Dolphin builds
|
||||||
|
GetQSettings().setValue(QStringLiteral("userstyle/enabled"), type == StyleType::User);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Settings::GetToolTipStyle(QColor& window_color, QColor& text_color,
|
void Settings::GetToolTipStyle(QColor& window_color, QColor& text_color,
|
||||||
|
|
|
@ -57,11 +57,26 @@ public:
|
||||||
void SetSystemDark(bool dark);
|
void SetSystemDark(bool dark);
|
||||||
bool IsSystemDark();
|
bool IsSystemDark();
|
||||||
bool IsThemeDark();
|
bool IsThemeDark();
|
||||||
void SetCurrentUserStyle(const QString& stylesheet_name);
|
|
||||||
QString GetCurrentUserStyle() const;
|
|
||||||
|
|
||||||
void SetUserStylesEnabled(bool enabled);
|
void SetUserStyleName(const QString& stylesheet_name);
|
||||||
bool AreUserStylesEnabled() const;
|
QString GetUserStyleName() const;
|
||||||
|
|
||||||
|
enum class StyleType : int
|
||||||
|
{
|
||||||
|
System = 0,
|
||||||
|
Light = 1,
|
||||||
|
Dark = 2,
|
||||||
|
User = 3,
|
||||||
|
|
||||||
|
MinValue = 0,
|
||||||
|
MaxValue = 3,
|
||||||
|
};
|
||||||
|
|
||||||
|
void SetStyleType(StyleType type);
|
||||||
|
StyleType GetStyleType() const;
|
||||||
|
|
||||||
|
// this evaluates the current stylesheet settings and refreshes the GUI with them
|
||||||
|
void ApplyStyle();
|
||||||
|
|
||||||
void GetToolTipStyle(QColor& window_color, QColor& text_color, QColor& emphasis_text_color,
|
void GetToolTipStyle(QColor& window_color, QColor& text_color, QColor& emphasis_text_color,
|
||||||
QColor& border_color, const QPalette& palette,
|
QColor& border_color, const QPalette& palette,
|
||||||
|
|
|
@ -128,12 +128,18 @@ void InterfacePane::CreateUI()
|
||||||
|
|
||||||
// User Style Combobox
|
// User Style Combobox
|
||||||
m_combobox_userstyle = new QComboBox;
|
m_combobox_userstyle = new QComboBox;
|
||||||
m_label_userstyle = new QLabel(tr("User Style:"));
|
m_label_userstyle = new QLabel(tr("Style:"));
|
||||||
combobox_layout->addRow(m_label_userstyle, m_combobox_userstyle);
|
combobox_layout->addRow(m_label_userstyle, m_combobox_userstyle);
|
||||||
|
|
||||||
auto userstyle_search_results = Common::DoFileSearch({File::GetUserPath(D_STYLES_IDX)});
|
auto userstyle_search_results = Common::DoFileSearch({File::GetUserPath(D_STYLES_IDX)});
|
||||||
|
|
||||||
m_combobox_userstyle->addItem(tr("(None)"), QString{});
|
m_combobox_userstyle->addItem(tr("(System)"), static_cast<int>(Settings::StyleType::System));
|
||||||
|
|
||||||
|
// TODO: Support forcing light/dark on other OSes too.
|
||||||
|
#ifdef _WIN32
|
||||||
|
m_combobox_userstyle->addItem(tr("(Light)"), static_cast<int>(Settings::StyleType::Light));
|
||||||
|
m_combobox_userstyle->addItem(tr("(Dark)"), static_cast<int>(Settings::StyleType::Dark));
|
||||||
|
#endif
|
||||||
|
|
||||||
for (const std::string& path : userstyle_search_results)
|
for (const std::string& path : userstyle_search_results)
|
||||||
{
|
{
|
||||||
|
@ -143,7 +149,6 @@ void InterfacePane::CreateUI()
|
||||||
|
|
||||||
// Checkboxes
|
// Checkboxes
|
||||||
m_checkbox_use_builtin_title_database = new QCheckBox(tr("Use Built-In Database of Game Names"));
|
m_checkbox_use_builtin_title_database = new QCheckBox(tr("Use Built-In Database of Game Names"));
|
||||||
m_checkbox_use_userstyle = new QCheckBox(tr("Use Custom User Style"));
|
|
||||||
m_checkbox_use_covers =
|
m_checkbox_use_covers =
|
||||||
new QCheckBox(tr("Download Game Covers from GameTDB.com for Use in Grid Mode"));
|
new QCheckBox(tr("Download Game Covers from GameTDB.com for Use in Grid Mode"));
|
||||||
m_checkbox_show_debugging_ui = new QCheckBox(tr("Enable Debugging UI"));
|
m_checkbox_show_debugging_ui = new QCheckBox(tr("Enable Debugging UI"));
|
||||||
|
@ -151,7 +156,6 @@ void InterfacePane::CreateUI()
|
||||||
m_checkbox_disable_screensaver = new QCheckBox(tr("Inhibit Screensaver During Emulation"));
|
m_checkbox_disable_screensaver = new QCheckBox(tr("Inhibit Screensaver During Emulation"));
|
||||||
|
|
||||||
groupbox_layout->addWidget(m_checkbox_use_builtin_title_database);
|
groupbox_layout->addWidget(m_checkbox_use_builtin_title_database);
|
||||||
groupbox_layout->addWidget(m_checkbox_use_userstyle);
|
|
||||||
groupbox_layout->addWidget(m_checkbox_use_covers);
|
groupbox_layout->addWidget(m_checkbox_use_covers);
|
||||||
groupbox_layout->addWidget(m_checkbox_show_debugging_ui);
|
groupbox_layout->addWidget(m_checkbox_show_debugging_ui);
|
||||||
groupbox_layout->addWidget(m_checkbox_focused_hotkeys);
|
groupbox_layout->addWidget(m_checkbox_focused_hotkeys);
|
||||||
|
@ -238,7 +242,6 @@ void InterfacePane::ConnectLayout()
|
||||||
&InterfacePane::OnCursorVisibleAlways);
|
&InterfacePane::OnCursorVisibleAlways);
|
||||||
connect(m_checkbox_lock_mouse, &QCheckBox::toggled, &Settings::Instance(),
|
connect(m_checkbox_lock_mouse, &QCheckBox::toggled, &Settings::Instance(),
|
||||||
&Settings::SetLockCursor);
|
&Settings::SetLockCursor);
|
||||||
connect(m_checkbox_use_userstyle, &QCheckBox::toggled, this, &InterfacePane::OnSaveConfig);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void InterfacePane::LoadConfig()
|
void InterfacePane::LoadConfig()
|
||||||
|
@ -254,19 +257,15 @@ void InterfacePane::LoadConfig()
|
||||||
->setCurrentIndex(
|
->setCurrentIndex(
|
||||||
m_combobox_theme->findText(QString::fromStdString(Config::Get(Config::MAIN_THEME_NAME))));
|
m_combobox_theme->findText(QString::fromStdString(Config::Get(Config::MAIN_THEME_NAME))));
|
||||||
|
|
||||||
const QString userstyle = Settings::Instance().GetCurrentUserStyle();
|
const Settings::StyleType style_type = Settings::Instance().GetStyleType();
|
||||||
const int index = m_combobox_userstyle->findData(QFileInfo(userstyle).fileName());
|
const QString userstyle = Settings::Instance().GetUserStyleName();
|
||||||
|
const int index = style_type == Settings::StyleType::User ?
|
||||||
|
m_combobox_userstyle->findData(userstyle) :
|
||||||
|
m_combobox_userstyle->findData(static_cast<int>(style_type));
|
||||||
|
|
||||||
if (index > 0)
|
if (index > 0)
|
||||||
SignalBlocking(m_combobox_userstyle)->setCurrentIndex(index);
|
SignalBlocking(m_combobox_userstyle)->setCurrentIndex(index);
|
||||||
|
|
||||||
SignalBlocking(m_checkbox_use_userstyle)->setChecked(Settings::Instance().AreUserStylesEnabled());
|
|
||||||
|
|
||||||
const bool visible = m_checkbox_use_userstyle->isChecked();
|
|
||||||
|
|
||||||
m_combobox_userstyle->setVisible(visible);
|
|
||||||
m_label_userstyle->setVisible(visible);
|
|
||||||
|
|
||||||
// Render Window Options
|
// Render Window Options
|
||||||
SignalBlocking(m_checkbox_top_window)
|
SignalBlocking(m_checkbox_top_window)
|
||||||
->setChecked(Settings::Instance().IsKeepWindowOnTopEnabled());
|
->setChecked(Settings::Instance().IsKeepWindowOnTopEnabled());
|
||||||
|
@ -297,13 +296,15 @@ void InterfacePane::OnSaveConfig()
|
||||||
Config::SetBase(Config::MAIN_USE_BUILT_IN_TITLE_DATABASE,
|
Config::SetBase(Config::MAIN_USE_BUILT_IN_TITLE_DATABASE,
|
||||||
m_checkbox_use_builtin_title_database->isChecked());
|
m_checkbox_use_builtin_title_database->isChecked());
|
||||||
Settings::Instance().SetDebugModeEnabled(m_checkbox_show_debugging_ui->isChecked());
|
Settings::Instance().SetDebugModeEnabled(m_checkbox_show_debugging_ui->isChecked());
|
||||||
Settings::Instance().SetUserStylesEnabled(m_checkbox_use_userstyle->isChecked());
|
const auto selected_style = m_combobox_userstyle->currentData();
|
||||||
Settings::Instance().SetCurrentUserStyle(m_combobox_userstyle->currentData().toString());
|
bool is_builtin_type = false;
|
||||||
|
const int style_type_int = selected_style.toInt(&is_builtin_type);
|
||||||
const bool visible = m_checkbox_use_userstyle->isChecked();
|
Settings::Instance().SetStyleType(is_builtin_type ?
|
||||||
|
static_cast<Settings::StyleType>(style_type_int) :
|
||||||
m_combobox_userstyle->setVisible(visible);
|
Settings::StyleType::User);
|
||||||
m_label_userstyle->setVisible(visible);
|
if (!is_builtin_type)
|
||||||
|
Settings::Instance().SetUserStyleName(selected_style.toString());
|
||||||
|
Settings::Instance().ApplyStyle();
|
||||||
|
|
||||||
// Render Window Options
|
// Render Window Options
|
||||||
Settings::Instance().SetKeepWindowOnTop(m_checkbox_top_window->isChecked());
|
Settings::Instance().SetKeepWindowOnTop(m_checkbox_top_window->isChecked());
|
||||||
|
|
|
@ -36,7 +36,6 @@ private:
|
||||||
QLabel* m_label_userstyle;
|
QLabel* m_label_userstyle;
|
||||||
QCheckBox* m_checkbox_top_window;
|
QCheckBox* m_checkbox_top_window;
|
||||||
QCheckBox* m_checkbox_use_builtin_title_database;
|
QCheckBox* m_checkbox_use_builtin_title_database;
|
||||||
QCheckBox* m_checkbox_use_userstyle;
|
|
||||||
QCheckBox* m_checkbox_show_debugging_ui;
|
QCheckBox* m_checkbox_show_debugging_ui;
|
||||||
QCheckBox* m_checkbox_focused_hotkeys;
|
QCheckBox* m_checkbox_focused_hotkeys;
|
||||||
QCheckBox* m_checkbox_use_covers;
|
QCheckBox* m_checkbox_use_covers;
|
||||||
|
|
Loading…
Reference in New Issue