fix: read GTK dark theme setting on Linux (#23678)
This commit is contained in:
parent
82924679fe
commit
fdf40ce07a
2 changed files with 45 additions and 4 deletions
|
@ -67,6 +67,7 @@
|
|||
#include "ui/base/x/x11_util.h"
|
||||
#include "ui/base/x/x11_util_internal.h"
|
||||
#include "ui/events/devices/x11/touch_factory_x11.h"
|
||||
#include "ui/gfx/color_utils.h"
|
||||
#include "ui/gfx/x/x11_types.h"
|
||||
#include "ui/gtk/gtk_ui.h"
|
||||
#include "ui/gtk/gtk_ui_delegate.h"
|
||||
|
@ -210,10 +211,36 @@ int X11EmptyErrorHandler(Display* d, XErrorEvent* error) {
|
|||
int X11EmptyIOErrorHandler(Display* d) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
// GTK does not provide a way to check if current theme is dark, so we compare
|
||||
// the text and background luminosity to get a result.
|
||||
// This trick comes from FireFox.
|
||||
void UpdateDarkThemeSetting() {
|
||||
float bg = color_utils::GetRelativeLuminance(gtk::GetBgColor("GtkLabel"));
|
||||
float fg = color_utils::GetRelativeLuminance(gtk::GetFgColor("GtkLabel"));
|
||||
bool is_dark = fg > bg;
|
||||
// Pass it to NativeUi theme, which is used by the nativeTheme module and most
|
||||
// places in Electron.
|
||||
ui::NativeTheme::GetInstanceForNativeUi()->set_use_dark_colors(is_dark);
|
||||
// Pass it to Web Theme, to make "prefers-color-scheme" media query work.
|
||||
ui::NativeTheme::GetInstanceForWeb()->set_use_dark_colors(is_dark);
|
||||
}
|
||||
#endif
|
||||
|
||||
} // namespace
|
||||
|
||||
#if defined(USE_X11)
|
||||
class DarkThemeObserver : public ui::NativeThemeObserver {
|
||||
public:
|
||||
DarkThemeObserver() = default;
|
||||
|
||||
// ui::NativeThemeObserver:
|
||||
void OnNativeThemeUpdated(ui::NativeTheme* observed_theme) override {
|
||||
UpdateDarkThemeSetting();
|
||||
}
|
||||
};
|
||||
#endif
|
||||
|
||||
// static
|
||||
ElectronBrowserMainParts* ElectronBrowserMainParts::self_ = nullptr;
|
||||
|
||||
|
@ -374,11 +401,19 @@ void ElectronBrowserMainParts::ToolkitInitialized() {
|
|||
// In Aura/X11, Gtk-based LinuxUI implementation is used.
|
||||
gtk_ui_delegate_ = std::make_unique<ui::GtkUiDelegateX11>(gfx::GetXDisplay());
|
||||
ui::GtkUiDelegate::SetInstance(gtk_ui_delegate_.get());
|
||||
views::LinuxUI::SetInstance(BuildGtkUi(ui::GtkUiDelegate::instance()));
|
||||
#endif
|
||||
views::LinuxUI* linux_ui = BuildGtkUi(gtk_ui_delegate_.get());
|
||||
views::LinuxUI::SetInstance(linux_ui);
|
||||
linux_ui->Initialize();
|
||||
|
||||
#if defined(USE_AURA) && defined(USE_X11)
|
||||
views::LinuxUI::instance()->Initialize();
|
||||
// Chromium does not respect GTK dark theme setting, but they may change
|
||||
// in future and this code might be no longer needed. Check the Chromium
|
||||
// issue to keep updated:
|
||||
// https://bugs.chromium.org/p/chromium/issues/detail?id=998903
|
||||
UpdateDarkThemeSetting();
|
||||
// Update the naitve theme when GTK theme changes. The GetNativeTheme
|
||||
// here returns a NativeThemeGtk, which monitors GTK settings.
|
||||
dark_theme_observer_.reset(new DarkThemeObserver);
|
||||
linux_ui->GetNativeTheme(nullptr)->AddObserver(dark_theme_observer_.get());
|
||||
#endif
|
||||
|
||||
#if defined(USE_AURA)
|
||||
|
|
|
@ -59,6 +59,10 @@ class ViewsDelegate;
|
|||
class ViewsDelegateMac;
|
||||
#endif
|
||||
|
||||
#if defined(USE_X11)
|
||||
class DarkThemeObserver;
|
||||
#endif
|
||||
|
||||
class ElectronBrowserMainParts : public content::BrowserMainParts {
|
||||
public:
|
||||
explicit ElectronBrowserMainParts(const content::MainFunctionParams& params);
|
||||
|
@ -129,6 +133,8 @@ class ElectronBrowserMainParts : public content::BrowserMainParts {
|
|||
|
||||
#if defined(USE_X11)
|
||||
std::unique_ptr<ui::GtkUiDelegate> gtk_ui_delegate_;
|
||||
// Used to notify the native theme of changes to dark mode.
|
||||
std::unique_ptr<DarkThemeObserver> dark_theme_observer_;
|
||||
#endif
|
||||
|
||||
std::unique_ptr<views::LayoutProvider> layout_provider_;
|
||||
|
|
Loading…
Reference in a new issue