diff --git a/Wino.Core.Domain/Interfaces/IPreferencesService.cs b/Wino.Core.Domain/Interfaces/IPreferencesService.cs index 51e7eb22..bced247d 100644 --- a/Wino.Core.Domain/Interfaces/IPreferencesService.cs +++ b/Wino.Core.Domain/Interfaces/IPreferencesService.cs @@ -6,7 +6,7 @@ using Wino.Core.Domain.Models.Reader; namespace Wino.Core.Domain.Interfaces; -public interface IPreferencesService: INotifyPropertyChanged +public interface IPreferencesService : INotifyPropertyChanged { /// /// When any of the preferences are changed. diff --git a/Wino.Core.WinUI/Interfaces/IWinoShellWindow.cs b/Wino.Core.WinUI/Interfaces/IWinoShellWindow.cs index 2a504fdf..67c07694 100644 --- a/Wino.Core.WinUI/Interfaces/IWinoShellWindow.cs +++ b/Wino.Core.WinUI/Interfaces/IWinoShellWindow.cs @@ -6,6 +6,7 @@ namespace Wino.Core.WinUI.Interfaces; public interface IWinoShellWindow { void HandleAppActivation(LaunchActivatedEventArgs args); - Microsoft.UI.Xaml.Controls.TitleBar GetTitleBar(); + TitleBar GetTitleBar(); Frame GetMainFrame(); + FrameworkElement GetRootContent(); } diff --git a/Wino.Core.WinUI/Services/ThemeService.cs b/Wino.Core.WinUI/Services/ThemeService.cs index 5a8bfbc0..1eb6e031 100644 --- a/Wino.Core.WinUI/Services/ThemeService.cs +++ b/Wino.Core.WinUI/Services/ThemeService.cs @@ -7,10 +7,9 @@ using System.Runtime.InteropServices.WindowsRuntime; using System.Text.Json; using System.Threading.Tasks; using CommunityToolkit.Mvvm.Messaging; +using CommunityToolkit.WinUI; using CommunityToolkit.WinUI.Helpers; -using Microsoft.UI; using Microsoft.UI.Xaml; -using Microsoft.UI.Xaml.Controls; using Microsoft.UI.Xaml.Markup; using Microsoft.UI.Xaml.Media; using Windows.Storage; @@ -23,6 +22,7 @@ using Wino.Core.Domain.Models; using Wino.Core.Domain.Models.Personalization; using Wino.Core.WinUI; using Wino.Core.WinUI.Extensions; +using Wino.Core.WinUI.Interfaces; using Wino.Core.WinUI.Models.Personalization; using Wino.Core.WinUI.Services; using Wino.Messaging.Client.Shell; @@ -44,8 +44,6 @@ public class ThemeService : IThemeService private static string _snowflakeThemeId = "e143ddde-2e28-4846-9d98-dad63d6505f1"; private static string _gardenThemeId = "698e4466-f88c-4799-9c61-f0ea1308ed49"; - private Frame mainApplicationFrame = null; - public event EventHandler ElementThemeChanged; public event EventHandler AccentColorChanged; @@ -89,16 +87,15 @@ public class ThemeService : IThemeService { get { - if (mainApplicationFrame == null) return ApplicationElementTheme.Default; + return GetShellRootContent().RequestedTheme.ToWinoElementTheme(); + //if (mainApplicationFrame == null) return ApplicationElementTheme.Default; - return mainApplicationFrame.RequestedTheme.ToWinoElementTheme(); + //return mainApplicationFrame.RequestedTheme.ToWinoElementTheme(); } set { - if (mainApplicationFrame == null) - return; - - mainApplicationFrame.RequestedTheme = value.ToWindowsElementTheme(); + GetShellRootContent().RequestedTheme = value.ToWindowsElementTheme(); + // mainApplicationFrame.RequestedTheme = value.ToWindowsElementTheme(); _configurationService.Set(UnderlyingThemeService.SelectedAppThemeKey, value); @@ -121,10 +118,13 @@ public class ThemeService : IThemeService _configurationService.Set(CurrentApplicationThemeKey, value); - _ = mainApplicationFrame.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.High, async () => + if (WinoApplication.MainWindow != null) { - await ApplyCustomThemeAsync(false); - }); + WinoApplication.MainWindow.DispatcherQueue.TryEnqueue(async () => + { + await ApplyCustomThemeAsync(false); + }); + } } } @@ -154,17 +154,14 @@ public class ThemeService : IThemeService } } + public FrameworkElement GetShellRootContent() => (WinoApplication.MainWindow as IWinoShellWindow)?.GetRootContent() ?? throw new Exception("No root content found"); + + private bool isInitialized = false; + public async Task InitializeAsync() { // Already initialized. There is no need. - if (mainApplicationFrame != null) - return; - - // Save reference as this might be null when the user is in another app - - mainApplicationFrame = WinoApplication.MainWindow.Content as Frame; - - if (mainApplicationFrame == null) return; + if (isInitialized) return; RootTheme = _configurationService.Get(UnderlyingThemeService.SelectedAppThemeKey, ApplicationElementTheme.Default); AccentColor = _configurationService.Get(AccentColorKey, string.Empty); @@ -177,56 +174,48 @@ public class ThemeService : IThemeService // Registering to color changes, thus we notice when user changes theme system wide uiSettings.ColorValuesChanged -= UISettingsColorChanged; uiSettings.ColorValuesChanged += UISettingsColorChanged; + + isInitialized = true; } private void NotifyThemeUpdate() { - if (mainApplicationFrame == null || mainApplicationFrame.Dispatcher == null) return; + if (GetShellRootContent() is not UIElement rootContent) return; - _ = mainApplicationFrame.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.High, () => + _ = rootContent.DispatcherQueue.EnqueueAsync(() => { ElementThemeChanged?.Invoke(this, RootTheme); WeakReferenceMessenger.Default.Send(new ApplicationThemeChanged(_underlyingThemeService.IsUnderlyingThemeDark())); - }); + }, Microsoft.UI.Dispatching.DispatcherQueuePriority.High); } private void UISettingsColorChanged(UISettings sender, object args) { - // Make sure we have a reference to our window so we dispatch a UI change - if (mainApplicationFrame != null) - { - // Dispatch on UI thread so that we have a current appbar to access and change - - _ = mainApplicationFrame.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.High, () => - { - UpdateSystemCaptionButtonColors(); - - var accentColor = sender.GetColorValue(UIColorType.Accent); - //AccentColorChangedBySystem?.Invoke(this, accentColor.ToHex()); - }); - } + // TODO: Buggy. + //GetShellRootContent().DispatcherQueue.TryEnqueue(() => + //{ + // UpdateSystemCaptionButtonColors(); + //}); NotifyThemeUpdate(); } public void UpdateSystemCaptionButtonColors() { - if (mainApplicationFrame == null) return; - - _ = mainApplicationFrame.Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () => + GetShellRootContent().DispatcherQueue.TryEnqueue(() => { - ApplicationViewTitleBar titleBar = ApplicationView.GetForCurrentView().TitleBar; + Debug.WriteLine("TODO: Updating caption button colors"); - if (titleBar == null) return; + // var titleBar = (WinoApplication.MainWindow as IWinoShellWindow).GetTitleBar(); - if (_underlyingThemeService.IsUnderlyingThemeDark()) - { - titleBar.ButtonForegroundColor = Colors.White; - } - else - { - titleBar.ButtonForegroundColor = Colors.Black; - } + //if (_underlyingThemeService.IsUnderlyingThemeDark()) + //{ + // titleBar.ButtonForegroundColor = Colors.White; + //} + //else + //{ + // titleBar.ButtonForegroundColor = Colors.Black; + //} }); } @@ -257,6 +246,8 @@ public class ThemeService : IThemeService private void RefreshThemeResource() { + var mainApplicationFrame = GetShellRootContent(); + if (mainApplicationFrame == null) return; if (mainApplicationFrame.RequestedTheme == ElementTheme.Dark) diff --git a/Wino.Mail.WinUI/AppShell.xaml b/Wino.Mail.WinUI/AppShell.xaml index 7bb288c3..13f7a210 100644 --- a/Wino.Mail.WinUI/AppShell.xaml +++ b/Wino.Mail.WinUI/AppShell.xaml @@ -356,22 +356,9 @@ - - - - - - - - - - - diff --git a/Wino.Mail.WinUI/AppShell.xaml.cs b/Wino.Mail.WinUI/AppShell.xaml.cs index 35e613a0..db0a259c 100644 --- a/Wino.Mail.WinUI/AppShell.xaml.cs +++ b/Wino.Mail.WinUI/AppShell.xaml.cs @@ -130,7 +130,7 @@ public sealed partial class AppShell : AppShellAbstract, public async void Receive(AccountMenuItemExtended message) { - await Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.High, async () => + await DispatcherQueue.EnqueueAsync(async () => { if (message.FolderId == default) return; diff --git a/Wino.Mail.WinUI/ShellWindow.xaml b/Wino.Mail.WinUI/ShellWindow.xaml index ab6f6681..3f8347d3 100644 --- a/Wino.Mail.WinUI/ShellWindow.xaml +++ b/Wino.Mail.WinUI/ShellWindow.xaml @@ -11,6 +11,7 @@ mc:Ignorable="d"> + @@ -20,8 +21,17 @@ - + - + diff --git a/Wino.Mail.WinUI/ShellWindow.xaml.cs b/Wino.Mail.WinUI/ShellWindow.xaml.cs index 2320df3a..2bde3953 100644 --- a/Wino.Mail.WinUI/ShellWindow.xaml.cs +++ b/Wino.Mail.WinUI/ShellWindow.xaml.cs @@ -1,6 +1,12 @@ +using System; +using CommunityToolkit.Mvvm.Messaging; +using Microsoft.Extensions.DependencyInjection; using Microsoft.UI.Xaml; using Microsoft.UI.Xaml.Controls; +using Wino.Core.Domain.Interfaces; +using Wino.Core.WinUI; using Wino.Core.WinUI.Interfaces; +using Wino.Messaging.Client.Mails; using Wino.Views; using WinUIEx; @@ -8,10 +14,15 @@ namespace Wino.Mail.WinUI; public sealed partial class ShellWindow : WindowEx, IWinoShellWindow { + public IStatePersistanceService StatePersistanceService { get; } = WinoApplication.Current.Services.GetService() ?? throw new Exception("StatePersistanceService not registered in DI container."); + public IPreferencesService PreferencesService { get; } = WinoApplication.Current.Services.GetService() ?? throw new Exception("PreferencesService not registered in DI container."); + public ShellWindow() { InitializeComponent(); + MinWidth = 420; + MinHeight = 420; ConfigureTitleBar(); } @@ -30,4 +41,19 @@ public sealed partial class ShellWindow : WindowEx, IWinoShellWindow public Microsoft.UI.Xaml.Controls.TitleBar GetTitleBar() => ShellTitleBar; public Frame GetMainFrame() => MainShellFrame; + + public FrameworkElement GetRootContent() => Content as Grid ?? throw new Exception("RootContent is not a Grid or empty."); + + private void BackButtonClicked(Microsoft.UI.Xaml.Controls.TitleBar sender, object args) + { + WeakReferenceMessenger.Default.Send(new ClearMailSelectionsRequested()); + WeakReferenceMessenger.Default.Send(new DisposeRenderingFrameRequested()); + } + + private void MainFrameNavigated(object sender, Microsoft.UI.Xaml.Navigation.NavigationEventArgs e) => ShellTitleBar.Content = (e.Content as BasePage).ShellContent; + + private void PaneButtonClicked(Microsoft.UI.Xaml.Controls.TitleBar sender, object args) + { + PreferencesService.IsNavigationPaneOpened = !PreferencesService.IsNavigationPaneOpened; + } }