mirror of
https://github.com/microsoft/PowerToys.git
synced 2025-01-18 06:29:44 +08:00
Theme aware plugin (#4499)
* Migrate theme manager to infrastructure and added it as input to public API instance * Working event-delegate for PublicAPIInstance * Theme aware UWP applications * Theme aware program plugin * Update query icon on theme change * Theme aware calculator plugin * Fix issue with query running before theme change * Theme based changes in ImageLoader * Removed ErrorIcon direct references and added references from ImageLoader * Nit fixes * Removed unnecessary TODO in UWP.cs * Added preference to theme based icons * Added IDisposable interfaces to unsubscribe events
This commit is contained in:
parent
d9597d5ad5
commit
d3b10d0d4d
Before Width: | Height: | Size: 597 B After Width: | Height: | Size: 597 B |
Binary file not shown.
After Width: | Height: | Size: 597 B |
@ -1,4 +1,6 @@
|
||||
using System.Collections.Generic;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Drawing;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Threading;
|
||||
@ -8,7 +10,7 @@ using Wox.Plugin;
|
||||
|
||||
namespace Microsoft.Plugin.Calculator
|
||||
{
|
||||
public class Main : IPlugin, IPluginI18n
|
||||
public class Main : IPlugin, IPluginI18n, IDisposable
|
||||
{
|
||||
private static readonly Regex RegValidExpressChar = new Regex(
|
||||
@"^(" +
|
||||
@ -22,6 +24,8 @@ namespace Microsoft.Plugin.Calculator
|
||||
private static readonly Regex RegBrackets = new Regex(@"[\(\)\[\]]", RegexOptions.Compiled);
|
||||
private static readonly Engine MagesEngine;
|
||||
private PluginInitContext Context { get; set; }
|
||||
private string IconPath { get; set; }
|
||||
private bool _disposed = false;
|
||||
|
||||
static Main()
|
||||
{
|
||||
@ -58,7 +62,7 @@ namespace Microsoft.Plugin.Calculator
|
||||
new Result
|
||||
{
|
||||
Title = result.ToString(),
|
||||
IcoPath = "Images/calculator.png",
|
||||
IcoPath = IconPath,
|
||||
Score = 300,
|
||||
SubTitle = Context.API.GetTranslation("wox_plugin_calculator_copy_number_to_clipboard"),
|
||||
Action = c =>
|
||||
@ -115,6 +119,26 @@ namespace Microsoft.Plugin.Calculator
|
||||
public void Init(PluginInitContext context)
|
||||
{
|
||||
Context = context;
|
||||
Context.API.ThemeChanged += OnThemeChanged;
|
||||
UpdateIconPath(Context.API.GetCurrentTheme());
|
||||
}
|
||||
|
||||
// Todo : Update with theme based IconPath
|
||||
private void UpdateIconPath(Theme theme)
|
||||
{
|
||||
if (theme == Theme.Light || theme == Theme.HighContrastWhite)
|
||||
{
|
||||
IconPath = "Images/calculator_light.png";
|
||||
}
|
||||
else
|
||||
{
|
||||
IconPath = "Images/calculator_dark.png";
|
||||
}
|
||||
}
|
||||
|
||||
private void OnThemeChanged(Theme _, Theme newTheme)
|
||||
{
|
||||
UpdateIconPath(newTheme);
|
||||
}
|
||||
|
||||
public string GetTranslatedPluginTitle()
|
||||
@ -126,5 +150,23 @@ namespace Microsoft.Plugin.Calculator
|
||||
{
|
||||
return Context.API.GetTranslation("wox_plugin_calculator_plugin_description");
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(disposing: true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
protected virtual void Dispose(bool disposing)
|
||||
{
|
||||
if (!_disposed)
|
||||
{
|
||||
if (disposing)
|
||||
{
|
||||
Context.API.ThemeChanged -= OnThemeChanged;
|
||||
_disposed = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -49,7 +49,7 @@
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Include="Images\calculator.png">
|
||||
<None Include="Images\calculator_light.png">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
</ItemGroup>
|
||||
@ -107,5 +107,11 @@
|
||||
<PackageReference Include="Mages" Version="1.6.0" />
|
||||
<PackageReference Include="System.Runtime" Version="4.3.1" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Update="Images\calculator_dark.png">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
@ -13,11 +13,11 @@ using Wox.Plugin;
|
||||
using Microsoft.Plugin.Program.Views;
|
||||
|
||||
using Stopwatch = Wox.Infrastructure.Stopwatch;
|
||||
|
||||
using Microsoft.Plugin.Program.Programs;
|
||||
|
||||
namespace Microsoft.Plugin.Program
|
||||
{
|
||||
public class Main : ISettingProvider, IPlugin, IPluginI18n, IContextMenu, ISavable, IReloadable
|
||||
public class Main : ISettingProvider, IPlugin, IPluginI18n, IContextMenu, ISavable, IReloadable, IDisposable
|
||||
{
|
||||
private static readonly object IndexLock = new object();
|
||||
internal static Programs.Win32[] _win32s { get; set; }
|
||||
@ -34,6 +34,7 @@ namespace Microsoft.Plugin.Program
|
||||
private static BinaryStorage<Programs.Win32[]> _win32Storage;
|
||||
private static BinaryStorage<Programs.UWP.Application[]> _uwpStorage;
|
||||
private readonly PluginJsonStorage<Settings> _settingsStorage;
|
||||
private bool _disposed = false;
|
||||
|
||||
public Main()
|
||||
{
|
||||
@ -104,6 +105,21 @@ namespace Microsoft.Plugin.Program
|
||||
public void Init(PluginInitContext context)
|
||||
{
|
||||
_context = context;
|
||||
_context.API.ThemeChanged += OnThemeChanged;
|
||||
UpdateUWPIconPath(_context.API.GetCurrentTheme());
|
||||
}
|
||||
|
||||
public void OnThemeChanged(Theme _, Theme currentTheme)
|
||||
{
|
||||
UpdateUWPIconPath(currentTheme);
|
||||
}
|
||||
|
||||
public void UpdateUWPIconPath(Theme theme)
|
||||
{
|
||||
foreach (UWP.Application app in _uwps)
|
||||
{
|
||||
app.UpdatePath(theme);
|
||||
}
|
||||
}
|
||||
|
||||
public static void IndexWin32Programs()
|
||||
@ -186,6 +202,25 @@ namespace Microsoft.Plugin.Program
|
||||
public void UpdateSettings(PowerLauncherSettings settings)
|
||||
{
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(disposing: true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
protected virtual void Dispose(bool disposing)
|
||||
{
|
||||
if (!_disposed)
|
||||
{
|
||||
if (disposing)
|
||||
{
|
||||
_context.API.ThemeChanged -= OnThemeChanged;
|
||||
_disposed = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void InitializeFileWatchers()
|
||||
{
|
||||
// Create a new FileSystemWatcher and set its properties.
|
||||
|
@ -21,6 +21,7 @@ using System.Windows.Input;
|
||||
using System.Runtime.InteropServices.ComTypes;
|
||||
using Wox.Plugin.SharedCommands;
|
||||
using System.Reflection;
|
||||
using Wox.Infrastructure.Image;
|
||||
|
||||
namespace Microsoft.Plugin.Program.Programs
|
||||
{
|
||||
@ -404,7 +405,6 @@ namespace Microsoft.Plugin.Program.Programs
|
||||
DisplayName = ResourceFromPri(package.FullName, DisplayName);
|
||||
Description = ResourceFromPri(package.FullName, Description);
|
||||
LogoUri = LogoUriFromManifest(manifestApp);
|
||||
LogoPath = LogoPathFromUri(LogoUri);
|
||||
|
||||
Enabled = true;
|
||||
CanRunElevated = IfApplicationcanRunElevated();
|
||||
@ -516,7 +516,19 @@ namespace Microsoft.Plugin.Program.Programs
|
||||
}
|
||||
}
|
||||
|
||||
internal string LogoPathFromUri(string uri)
|
||||
public void UpdatePath(Theme theme)
|
||||
{
|
||||
if (theme == Theme.Light || theme == Theme.HighContrastWhite)
|
||||
{
|
||||
LogoPath = LogoPathFromUri(LogoUri, "contrast-white");
|
||||
}
|
||||
else
|
||||
{
|
||||
LogoPath = LogoPathFromUri(LogoUri, "contrast-black");
|
||||
}
|
||||
}
|
||||
|
||||
internal string LogoPathFromUri(string uri, string theme)
|
||||
{
|
||||
// all https://msdn.microsoft.com/windows/uwp/controls-and-patterns/tiles-and-notifications-app-assets
|
||||
// windows 10 https://msdn.microsoft.com/en-us/library/windows/apps/dn934817.aspx
|
||||
@ -539,11 +551,7 @@ namespace Microsoft.Plugin.Program.Programs
|
||||
{
|
||||
var end = path.Length - extension.Length;
|
||||
var prefix = path.Substring(0, end);
|
||||
var paths = new List<string> { path };
|
||||
|
||||
// TODO: This value must be set in accordance to the WPF theme (work in progress).
|
||||
// Must be set to `contrast-white` for light theme and to `contrast-black` for dark theme to get an icon of the contrasting color.
|
||||
var theme = "contrast-black";
|
||||
var paths = new List<string> { path };
|
||||
|
||||
var scaleFactors = new Dictionary<PackageVersion, List<int>>
|
||||
{
|
||||
@ -563,6 +571,7 @@ namespace Microsoft.Plugin.Program.Programs
|
||||
}
|
||||
}
|
||||
|
||||
paths = paths.OrderByDescending(x => x.Contains(theme)).ToList();
|
||||
var selected = paths.FirstOrDefault(File.Exists);
|
||||
if (!string.IsNullOrEmpty(selected))
|
||||
{
|
||||
@ -589,6 +598,7 @@ namespace Microsoft.Plugin.Program.Programs
|
||||
pathFactorPairs.Add(prefixThemePath, factor);
|
||||
}
|
||||
|
||||
paths = paths.OrderByDescending(x => x.Contains(theme)).ToList();
|
||||
var selectedIconPath = paths.OrderBy(x => Math.Abs(pathFactorPairs.GetValueOrDefault(x) - appIconSize)).FirstOrDefault(File.Exists);
|
||||
if (!string.IsNullOrEmpty(selectedIconPath))
|
||||
{
|
||||
@ -630,7 +640,7 @@ namespace Microsoft.Plugin.Program.Programs
|
||||
ProgramLogger.LogException($"|UWP|ImageFromPath|{path}" +
|
||||
$"|Unable to get logo for {UserModelId} from {path} and" +
|
||||
$" located in {Package.Location}", new FileNotFoundException());
|
||||
return new BitmapImage(new Uri(Constant.ErrorIcon));
|
||||
return new BitmapImage(new Uri(ImageLoader.ErrorIconPath));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -17,6 +17,7 @@ using Wox.Infrastructure.Http;
|
||||
using Wox.Infrastructure.Image;
|
||||
using Wox.Infrastructure.Logger;
|
||||
using Wox.Infrastructure.UserSettings;
|
||||
using Wox.Plugin;
|
||||
using Wox.ViewModel;
|
||||
using Stopwatch = Wox.Infrastructure.Stopwatch;
|
||||
|
||||
@ -31,6 +32,7 @@ namespace PowerLauncher
|
||||
private Settings _settings;
|
||||
private MainViewModel _mainVM;
|
||||
private MainWindow _mainWindow;
|
||||
private ThemeManager _themeManager;
|
||||
private SettingWindowViewModel _settingsVM;
|
||||
private readonly Alphabet _alphabet = new Alphabet();
|
||||
private StringMatcher _stringMatcher;
|
||||
@ -70,7 +72,8 @@ namespace PowerLauncher
|
||||
RegisterAppDomainExceptions();
|
||||
RegisterDispatcherUnhandledException();
|
||||
|
||||
ImageLoader.Initialize();
|
||||
_themeManager = new ThemeManager(this);
|
||||
ImageLoader.Initialize(_themeManager.GetCurrentTheme());
|
||||
|
||||
_settingsVM = new SettingWindowViewModel();
|
||||
_settings = _settingsVM.Settings;
|
||||
@ -80,11 +83,10 @@ namespace PowerLauncher
|
||||
StringMatcher.Instance = _stringMatcher;
|
||||
_stringMatcher.UserSettingSearchPrecision = _settings.QuerySearchPrecision;
|
||||
|
||||
ThemeManager themeManager = new ThemeManager(this);
|
||||
PluginManager.LoadPlugins(_settings.PluginSettings);
|
||||
_mainVM = new MainViewModel(_settings);
|
||||
_mainWindow = new MainWindow(_settings, _mainVM);
|
||||
API = new PublicAPIInstance(_settingsVM, _mainVM, _alphabet);
|
||||
API = new PublicAPIInstance(_settingsVM, _mainVM, _alphabet, _themeManager);
|
||||
PluginManager.InitializePlugins(API);
|
||||
|
||||
Current.MainWindow = _mainWindow;
|
||||
@ -105,6 +107,7 @@ namespace PowerLauncher
|
||||
|
||||
_mainVM.MainWindowVisibility = Visibility.Visible;
|
||||
_mainVM.ColdStartFix();
|
||||
_themeManager.ThemeChanged += OnThemeChanged;
|
||||
Log.Info("|App.OnStartup|End PowerToys Run startup ---------------------------------------------------- ");
|
||||
|
||||
bootTime.Stop();
|
||||
@ -125,6 +128,17 @@ namespace PowerLauncher
|
||||
Current.SessionEnding += (s, e) => Dispose();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Callback when windows theme is changed.
|
||||
/// </summary>
|
||||
/// <param name="oldTheme">Previous Theme</param>
|
||||
/// <param name="newTheme">Current Theme</param>
|
||||
private void OnThemeChanged(Theme oldTheme, Theme newTheme)
|
||||
{
|
||||
ImageLoader.UpdateIconPath(newTheme);
|
||||
_mainVM.Query();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// let exception throw as normal is better for Debug
|
||||
/// </summary>
|
||||
@ -158,9 +172,13 @@ namespace PowerLauncher
|
||||
Log.Info("|App.OnExit| Start PowerToys Run Exit---------------------------------------------------- ");
|
||||
if (disposing)
|
||||
{
|
||||
_mainWindow.Dispose();
|
||||
_themeManager.ThemeChanged -= OnThemeChanged;
|
||||
API.SaveAppAllSettings();
|
||||
PluginManager.Dispose();
|
||||
_mainWindow.Dispose();
|
||||
API.Dispose();
|
||||
_mainVM.Dispose();
|
||||
_themeManager.Dispose();
|
||||
_disposed = true;
|
||||
}
|
||||
|
||||
|
@ -287,5 +287,14 @@ namespace Wox.Core.Plugin
|
||||
RemoveActionKeyword(id, oldActionKeyword);
|
||||
}
|
||||
}
|
||||
|
||||
public static void Dispose()
|
||||
{
|
||||
foreach (var plugin in AllPlugins)
|
||||
{
|
||||
var disposablePlugin = plugin as IDisposable;
|
||||
disposablePlugin?.Dispose();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -57,7 +57,6 @@
|
||||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||
</PackageReference>
|
||||
<PackageReference Include="JetBrains.Annotations" Version="2020.1.0" />
|
||||
<PackageReference Include="MahApps.Metro" Version="2.0.0" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="12.0.3" />
|
||||
<PackageReference Include="PropertyChanged.Fody" Version="3.2.8" />
|
||||
<PackageReference Include="SharpZipLib" Version="1.2.0" />
|
||||
|
@ -8,6 +8,7 @@ using System.Windows.Media;
|
||||
using System.Windows.Media.Imaging;
|
||||
using Wox.Infrastructure.Logger;
|
||||
using Wox.Infrastructure.Storage;
|
||||
using Wox.Plugin;
|
||||
|
||||
namespace Wox.Infrastructure.Image
|
||||
{
|
||||
@ -17,7 +18,8 @@ namespace Wox.Infrastructure.Image
|
||||
private static BinaryStorage<Dictionary<string, int>> _storage;
|
||||
private static readonly ConcurrentDictionary<string, string> GuidToKey = new ConcurrentDictionary<string, string>();
|
||||
private static IImageHashGenerator _hashGenerator;
|
||||
|
||||
public static string ErrorIconPath;
|
||||
public static string DefaultIconPath;
|
||||
|
||||
private static readonly string[] ImageExtensions =
|
||||
{
|
||||
@ -31,18 +33,20 @@ namespace Wox.Infrastructure.Image
|
||||
};
|
||||
|
||||
|
||||
public static void Initialize()
|
||||
public static void Initialize(Theme theme)
|
||||
{
|
||||
_storage = new BinaryStorage<Dictionary<string, int>>("Image");
|
||||
_hashGenerator = new ImageHashGenerator();
|
||||
ImageCache.SetUsageAsDictionary(_storage.TryLoad(new Dictionary<string, int>()));
|
||||
|
||||
// Todo : Add error and default icon specific to each theme
|
||||
foreach (var icon in new[] { Constant.DefaultIcon, Constant.ErrorIcon })
|
||||
{
|
||||
ImageSource img = new BitmapImage(new Uri(icon));
|
||||
img.Freeze();
|
||||
ImageCache[icon] = img;
|
||||
}
|
||||
UpdateIconPath(theme);
|
||||
Task.Run(() =>
|
||||
{
|
||||
Stopwatch.Normal("|ImageLoader.Initialize|Preload images cost", () =>
|
||||
@ -62,6 +66,21 @@ namespace Wox.Infrastructure.Image
|
||||
_storage.Save(ImageCache.GetUsageAsDictionary());
|
||||
}
|
||||
|
||||
//Todo : Update it with icons specific to each theme.
|
||||
public static void UpdateIconPath(Theme theme)
|
||||
{
|
||||
if (theme == Theme.Light || theme == Theme.HighContrastWhite)
|
||||
{
|
||||
ErrorIconPath = Constant.ErrorIcon;
|
||||
DefaultIconPath = Constant.DefaultIcon;
|
||||
}
|
||||
else
|
||||
{
|
||||
ErrorIconPath = Constant.ErrorIcon;
|
||||
DefaultIconPath = Constant.DefaultIcon;
|
||||
}
|
||||
}
|
||||
|
||||
private class ImageResult
|
||||
{
|
||||
public ImageResult(ImageSource imageSource, ImageType imageType)
|
||||
@ -92,7 +111,7 @@ namespace Wox.Infrastructure.Image
|
||||
{
|
||||
if (string.IsNullOrEmpty(path))
|
||||
{
|
||||
return new ImageResult(ImageCache[Constant.ErrorIcon], ImageType.Error);
|
||||
return new ImageResult(ImageCache[ErrorIconPath], ImageType.Error);
|
||||
}
|
||||
if (ImageCache.ContainsKey(path))
|
||||
{
|
||||
@ -154,8 +173,8 @@ namespace Wox.Infrastructure.Image
|
||||
}
|
||||
else
|
||||
{
|
||||
image = ImageCache[Constant.ErrorIcon];
|
||||
path = Constant.ErrorIcon;
|
||||
image = ImageCache[ErrorIconPath];
|
||||
path = ErrorIconPath;
|
||||
}
|
||||
|
||||
if (type != ImageType.Error)
|
||||
@ -167,7 +186,7 @@ namespace Wox.Infrastructure.Image
|
||||
{
|
||||
Log.Exception($"|ImageLoader.Load|Failed to get thumbnail for {path}", e);
|
||||
type = ImageType.Error;
|
||||
image = ImageCache[Constant.ErrorIcon];
|
||||
image = ImageCache[ErrorIconPath];
|
||||
ImageCache[path] = image;
|
||||
}
|
||||
return new ImageResult(image, type);
|
||||
|
@ -57,6 +57,16 @@ namespace Wox.Plugin
|
||||
[Obsolete]
|
||||
void ShowApp();
|
||||
|
||||
/// <summary>
|
||||
/// Get current theme
|
||||
/// </summary>
|
||||
Theme GetCurrentTheme();
|
||||
|
||||
/// <summary>
|
||||
/// Theme change event
|
||||
/// </summary>
|
||||
event ThemeChangedHandler ThemeChanged;
|
||||
|
||||
/// <summary>
|
||||
/// Save all Wox settings
|
||||
/// </summary>
|
||||
|
@ -6,12 +6,13 @@ using System.Diagnostics;
|
||||
using System.Linq;
|
||||
using System.Windows;
|
||||
|
||||
namespace Wox.Core.Resource
|
||||
namespace Wox.Plugin
|
||||
{
|
||||
public class ThemeManager
|
||||
public class ThemeManager : IDisposable
|
||||
{
|
||||
private Theme currentTheme;
|
||||
private readonly Application App;
|
||||
private bool _disposed = false;
|
||||
private readonly string LightTheme = "Light.Accent1";
|
||||
private readonly string DarkTheme = "Dark.Accent1";
|
||||
private readonly string HighContrastOneTheme = "HighContrast.Accent2";
|
||||
@ -19,6 +20,8 @@ namespace Wox.Core.Resource
|
||||
private readonly string HighContrastBlackTheme = "HighContrast.Accent4";
|
||||
private readonly string HighContrastWhiteTheme = "HighContrast.Accent5";
|
||||
|
||||
public event ThemeChangedHandler ThemeChanged;
|
||||
|
||||
public ThemeManager(Application app)
|
||||
{
|
||||
this.App = app;
|
||||
@ -52,17 +55,23 @@ namespace Wox.Core.Resource
|
||||
ResetTheme();
|
||||
ControlzEx.Theming.ThemeManager.Current.ThemeSyncMode = ThemeSyncMode.SyncWithAppMode;
|
||||
ControlzEx.Theming.ThemeManager.Current.ThemeChanged += Current_ThemeChanged;
|
||||
SystemParameters.StaticPropertyChanged += (sender, args) =>
|
||||
SystemParameters.StaticPropertyChanged += SystemParameters_StaticPropertyChanged;
|
||||
}
|
||||
|
||||
private void SystemParameters_StaticPropertyChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e)
|
||||
{
|
||||
if (e.PropertyName == nameof(SystemParameters.HighContrast))
|
||||
{
|
||||
if (args.PropertyName == nameof(SystemParameters.HighContrast))
|
||||
{
|
||||
ResetTheme();
|
||||
}
|
||||
};
|
||||
ResetTheme();
|
||||
}
|
||||
}
|
||||
|
||||
public Theme GetCurrentTheme()
|
||||
{
|
||||
return currentTheme;
|
||||
}
|
||||
|
||||
|
||||
public static Theme GetHighContrastBaseType()
|
||||
private static Theme GetHighContrastBaseType()
|
||||
{
|
||||
string RegistryKey = @"HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Themes";
|
||||
string theme = (string) Registry.GetValue(RegistryKey, "CurrentTheme", string.Empty);
|
||||
@ -80,7 +89,7 @@ namespace Wox.Core.Resource
|
||||
return Theme.None;
|
||||
}
|
||||
|
||||
public void ResetTheme()
|
||||
private void ResetTheme()
|
||||
{
|
||||
if (SystemParameters.HighContrast)
|
||||
{
|
||||
@ -96,6 +105,7 @@ namespace Wox.Core.Resource
|
||||
|
||||
private void ChangeTheme(Theme theme)
|
||||
{
|
||||
Theme oldTheme = currentTheme;
|
||||
if (theme == currentTheme)
|
||||
return;
|
||||
if (theme == Theme.HighContrastOne)
|
||||
@ -132,15 +142,36 @@ namespace Wox.Core.Resource
|
||||
{
|
||||
currentTheme = Theme.None;
|
||||
}
|
||||
Debug.WriteLine("Theme Changed to :" + currentTheme);
|
||||
ThemeChanged?.Invoke(oldTheme, currentTheme);
|
||||
}
|
||||
|
||||
private void Current_ThemeChanged(object sender, ThemeChangedEventArgs e)
|
||||
{
|
||||
ResetTheme();
|
||||
}
|
||||
|
||||
protected virtual void Dispose(bool disposing)
|
||||
{
|
||||
if (!_disposed)
|
||||
{
|
||||
if (disposing)
|
||||
{
|
||||
ControlzEx.Theming.ThemeManager.Current.ThemeChanged -= Current_ThemeChanged;
|
||||
SystemParameters.StaticPropertyChanged -= SystemParameters_StaticPropertyChanged;
|
||||
_disposed = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(disposing: true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
}
|
||||
|
||||
public delegate void ThemeChangedHandler(Theme oldTheme, Theme newTheme);
|
||||
|
||||
public enum Theme
|
||||
{
|
||||
None,
|
@ -57,6 +57,8 @@
|
||||
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||
</PackageReference>
|
||||
<PackageReference Include="JetBrains.Annotations" Version="2020.1.0" />
|
||||
<PackageReference Include="MahApps.Metro" Version="2.1.0" />
|
||||
<PackageReference Include="ControlzEx" Version="4.3.0" />
|
||||
<PackageReference Include="Mono.Cecil" Version="0.11.2" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="12.0.3" />
|
||||
<PackageReference Include="PropertyChanged.Fody" Version="3.2.8" />
|
||||
|
@ -14,19 +14,25 @@ using Wox.ViewModel;
|
||||
|
||||
namespace Wox
|
||||
{
|
||||
public class PublicAPIInstance : IPublicAPI
|
||||
public class PublicAPIInstance : IPublicAPI, IDisposable
|
||||
{
|
||||
private readonly SettingWindowViewModel _settingsVM;
|
||||
private readonly MainViewModel _mainVM;
|
||||
private readonly Alphabet _alphabet;
|
||||
private bool _disposed = false;
|
||||
private readonly ThemeManager _themeManager;
|
||||
|
||||
public event ThemeChangedHandler ThemeChanged;
|
||||
|
||||
#region Constructor
|
||||
|
||||
public PublicAPIInstance(SettingWindowViewModel settingsVM, MainViewModel mainVM, Alphabet alphabet)
|
||||
public PublicAPIInstance(SettingWindowViewModel settingsVM, MainViewModel mainVM, Alphabet alphabet, ThemeManager themeManager)
|
||||
{
|
||||
_settingsVM = settingsVM;
|
||||
_mainVM = mainVM;
|
||||
_alphabet = alphabet;
|
||||
_themeManager = themeManager;
|
||||
_themeManager.ThemeChanged += OnThemeChanged;
|
||||
WebRequest.RegisterPrefix("data", new DataWebRequestFactory());
|
||||
}
|
||||
|
||||
@ -138,10 +144,37 @@ namespace Wox
|
||||
});
|
||||
}
|
||||
|
||||
public Theme GetCurrentTheme()
|
||||
{
|
||||
return _themeManager.GetCurrentTheme();
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(disposing: true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region Private Methods
|
||||
#region Protected Methods
|
||||
|
||||
protected void OnThemeChanged(Theme oldTheme, Theme newTheme)
|
||||
{
|
||||
ThemeChanged?.Invoke(oldTheme, newTheme);
|
||||
}
|
||||
|
||||
protected virtual void Dispose(bool disposing)
|
||||
{
|
||||
if (!_disposed)
|
||||
{
|
||||
if (disposing)
|
||||
{
|
||||
_themeManager.ThemeChanged -= OnThemeChanged;
|
||||
_disposed = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
|
@ -172,7 +172,7 @@ namespace Wox.ViewModel
|
||||
catch (Exception e)
|
||||
{
|
||||
Log.Exception($"|ResultViewModel.Image|IcoPath is empty and exception when calling Icon() for result <{Result.Title}> of plugin <{Result.PluginDirectory}>", e);
|
||||
imagePath = Constant.ErrorIcon;
|
||||
imagePath = ImageLoader.ErrorIconPath;
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user