From 4a02c508145b80daab285ac342bf2d85857d8e63 Mon Sep 17 00:00:00 2001 From: Sebastian Ratz Date: Thu, 13 Feb 2025 13:51:08 +0100 Subject: [PATCH] Respect user light/dark preference when restoring nonexistent theme When restoring a theme from preferences, which does not exist anymore. we previously fell back to inherting from the operating system. However, when when the user actively set the Eclipse theme to not match the light/dark mode of the OS, we would then fall back again to inheritance and override the user's choice. To improve this, we look at the preference the user had actively chosen before and see whether that was a dark theme or not and decide on that which theme to fall back to. Note: To check whether the theme is light or dark, we use the same heuristic also used in other places, themeId.contains("dark"): - org.eclipse.e4.ui.swt.internal.gtk.DarkThemeProcessor - org.eclipse.e4.ui.swt.internal.win32.DarkThemeProcessor - org.eclipse.e4.ui.swt.internal.cocoa.CocoaDarkThemeProcessor Future improvements to consider, out of scope for this change: - Move the heuristic themeId.contains("dark") to central place and to re-use - Even better, add an explicit "isDark" flag / preference somewhere - On top of that, use a mode=dark/light/followSystem instead, see also #2440. --- .../css/swt/internal/theme/ThemeEngine.java | 34 +++++++++++++------ 1 file changed, 23 insertions(+), 11 deletions(-) diff --git a/bundles/org.eclipse.e4.ui.css.swt.theme/src/org/eclipse/e4/ui/css/swt/internal/theme/ThemeEngine.java b/bundles/org.eclipse.e4.ui.css.swt.theme/src/org/eclipse/e4/ui/css/swt/internal/theme/ThemeEngine.java index 970658a7e4c..ad3aeac9719 100644 --- a/bundles/org.eclipse.e4.ui.css.swt.theme/src/org/eclipse/e4/ui/css/swt/internal/theme/ThemeEngine.java +++ b/bundles/org.eclipse.e4.ui.css.swt.theme/src/org/eclipse/e4/ui/css/swt/internal/theme/ThemeEngine.java @@ -588,27 +588,39 @@ public void restore(String alternateTheme) { prefThemeId = "org.eclipse.e4.ui.css.theme.e4_classic"; //$NON-NLS-1$ } - boolean flag = true; + // use theme from preferences if it exists if (prefThemeId != null) { for (ITheme t : getThemes()) { if (prefThemeId.equals(t.getId())) { setTheme(t, false); - flag = false; - break; + return; } } } - /* - * Any Platform: if the system has Dark appearance set and Eclipse is using the - * default settings, then start Eclipse in Dark theme. Check that there is a - * dark theme present. Can be disabled using a system property. - */ boolean hasDarkTheme = getThemes().stream().anyMatch(t -> t.getId().startsWith(E4_DARK_THEME_ID)); - boolean disableOSDarkThemeInherit = "true".equalsIgnoreCase(System.getProperty(DISABLE_OS_DARK_THEME_INHERIT)); - boolean overrideWithDarkTheme = Display.isSystemDarkTheme() && hasDarkTheme && !disableOSDarkThemeInherit; + boolean overrideWithDarkTheme = false; + if (hasDarkTheme) { + if (prefThemeId != null) { + /* + * The user had previously selected a theme which is not available anymore. In + * this case want to fall back to respect whether that previous choice was dark + * or not. https://github.com/eclipse-platform/eclipse.platform.ui/issues/2776 + */ + overrideWithDarkTheme = prefThemeId.contains("dark"); + } else { + /* + * No previous theme selection in preferences. In this case check if the system + * has dark appearance set and let Eclipse inherit that. Can be disabled using a + * system property. + */ + overrideWithDarkTheme = Display.isSystemDarkTheme() + && !"true".equalsIgnoreCase(System.getProperty(DISABLE_OS_DARK_THEME_INHERIT)); + } + } + String themeToRestore = overrideWithDarkTheme ? E4_DARK_THEME_ID : alternateTheme; - if (themeToRestore != null && flag) { + if (themeToRestore != null) { setTheme(themeToRestore, false); } }