From 6dc8956d0909211d8f5e0c4805e330a03071b1fb Mon Sep 17 00:00:00 2001 From: Violet Hansen Date: Mon, 23 Dec 2024 08:56:01 +0200 Subject: [PATCH] Configured default app settings (#475) The Sidebar's auto-assignment feature is now enabled by default to streamline user interactions. The check for updates at app startup is now on by default. It simply checks to see if a new version of the app is available and informs the user if there is by showing a small dot on the update page's icon. Both changes only apply to new app installations. If you've already toggled their buttons off then they remain off. A border has been added to the error dialog box, styled to match the current Windows accent color. --- AppControl Manager/App.xaml.cs | 9 ++++ AppControl Manager/AppSettings/AppSettings.cs | 44 +++++++++++++++++-- AppControl Manager/MainWindow.xaml.cs | 9 ++-- AppControl Manager/Pages/Update.xaml.cs | 16 ++++--- 4 files changed, 65 insertions(+), 13 deletions(-) diff --git a/AppControl Manager/App.xaml.cs b/AppControl Manager/App.xaml.cs index 03953544f..570c47efb 100644 --- a/AppControl Manager/App.xaml.cs +++ b/AppControl Manager/App.xaml.cs @@ -6,6 +6,7 @@ using CommunityToolkit.WinUI; using Microsoft.UI.Xaml; using Microsoft.UI.Xaml.Controls; +using Microsoft.UI.Xaml.Media; using Windows.ApplicationModel; // To learn more about WinUI abd the WinUI project structure see: http://aka.ms/winui-project-info @@ -42,6 +43,11 @@ public App() { this.InitializeComponent(); +#if DEBUG + + Logger.Write("App Startup"); +#endif + // Give beautiful outline to the UI elements when using the tab key and keyboard for navigation // https://learn.microsoft.com/en-us/windows/apps/design/style/reveal-focus this.FocusVisualKind = FocusVisualKind.Reveal; @@ -176,9 +182,12 @@ private async Task ShowErrorDialogAsync(Exception ex) // Ensure we're on the UI thread before showing the dialog await m_window.DispatcherQueue.EnqueueAsync(async () => { + ContentDialog errorDialog = new() { Title = "An error occurred", + BorderBrush = Current.Resources["AccentFillColorDefaultBrush"] as Brush ?? new SolidColorBrush(Colors.Transparent), + BorderThickness = new Thickness(1), Content = $"An unexpected error has occurred:\n{ex.Message}", CloseButtonText = "OK", XamlRoot = m_window.Content.XamlRoot // Ensure dialog is attached to the main window diff --git a/AppControl Manager/AppSettings/AppSettings.cs b/AppControl Manager/AppSettings/AppSettings.cs index 6ba91e04b..61dd3ad21 100644 --- a/AppControl Manager/AppSettings/AppSettings.cs +++ b/AppControl Manager/AppSettings/AppSettings.cs @@ -6,14 +6,23 @@ namespace AppControlManager; internal static class AppSettings { - // Save setting to local storage with a specific key and value + /// + /// Save setting to local storage with a specific key and value + /// + /// + /// internal static void SaveSetting(SettingKeys key, object? value) { ApplicationDataContainer localSettings = ApplicationData.Current.LocalSettings; localSettings.Values[key.ToString()] = value; } - // Retrieve setting from local storage with a specific key + /// + /// Retrieve setting from local storage with a specific key + /// + /// + /// + /// internal static T? GetSetting(SettingKeys key) { ApplicationDataContainer localSettings = ApplicationData.Current.LocalSettings; @@ -30,6 +39,34 @@ internal static void SaveSetting(SettingKeys key, object? value) } + /// + /// Retrieve setting from local storage with a specific key and returns null if the value doesn't exist. + /// Used by settings that need to set a default app configuration to true/on unless there is a user-defined configuration. + /// + /// + /// + /// + internal static T? TryGetSetting(SettingKeys key) + { + ApplicationDataContainer localSettings = ApplicationData.Current.LocalSettings; + + // Check if the key exists and get the value + if (localSettings.Values.TryGetValue(key.ToString(), out object? value)) + { + // Return value cast to T (for value types, this works with nullable types as well) + return value is T result ? result : default; + } + + // Return null explicitly when the key does not exist + // If T is a reference type, return null directly. + // If T is a value type, check if it supports nullable by comparing default(T?) to null. + // If T is not nullable (e.g., int), cast null to T? and return it, effectively providing a null result. + // in other words: + // calling it like this: AppSettings.GetSetting(AppSettings.SettingKeys.AutomaticAssignmentSidebar); and if the key doesn't exist, returns default value for bool which is false. + // Calling it like this: AppSettings.GetSetting(AppSettings.SettingKeys.AutomaticAssignmentSidebar); and if the key doesn't exist, returns null. + return default(T?) == null ? default : (T?)(object?)null; + } + // Enum for the setting keys // Used when saving and retrieving settings internal enum SettingKeys @@ -43,6 +80,7 @@ internal enum SettingKeys MainWindowWidth, MainWindowHeight, MainWindowIsMaximized, - AutomaticAssignmentSidebar + AutomaticAssignmentSidebar, + AutoCheckForUpdateAtStartup } } diff --git a/AppControl Manager/MainWindow.xaml.cs b/AppControl Manager/MainWindow.xaml.cs index 4f44ac6ef..7181193e1 100644 --- a/AppControl Manager/MainWindow.xaml.cs +++ b/AppControl Manager/MainWindow.xaml.cs @@ -291,12 +291,13 @@ static IEnumerable GetAllChildren(NavigationViewItem parent) _ = Task.Run(() => { - // If AutoUpdateCheck is enabled in the user configurations, checks for updates on startup and displays a dot on the Update page in the navigation + // If AutoCheckForUpdateAtStartup is enabled in the app settings, checks for updates on startup and displays a dot on the Update page in the navigation // If a new version is available. - if (UserConfiguration.Get().AutoUpdateCheck == true) + // Will also check for update if it's null meaning user hasn't configured the auto update check yet + if (AppSettings.TryGetSetting(AppSettings.SettingKeys.AutoCheckForUpdateAtStartup) ?? true) { - Logger.Write("Checking for update on startup because AutoUpdateCheck is enabled"); + Logger.Write("Checking for update on startup"); // Start the update check UpdateCheckResponse updateCheckResponse = updateService.Check(); @@ -1610,7 +1611,7 @@ private void RootGrid_Loaded(object sender, RoutedEventArgs e) SidebarBasePolicyPathTextBox.Text = UserConfiguration.Get().UnsignedPolicyPath; // Set the status of the sidebar toggle switch for auto assignment by getting it from saved app settings - AutomaticAssignmentSidebarToggleSwitch.IsOn = AppSettings.GetSetting(AppSettings.SettingKeys.AutomaticAssignmentSidebar); + AutomaticAssignmentSidebarToggleSwitch.IsOn = AppSettings.TryGetSetting(AppSettings.SettingKeys.AutomaticAssignmentSidebar) ?? true; } diff --git a/AppControl Manager/Pages/Update.xaml.cs b/AppControl Manager/Pages/Update.xaml.cs index 58f4c0b5b..411e31f6b 100644 --- a/AppControl Manager/Pages/Update.xaml.cs +++ b/AppControl Manager/Pages/Update.xaml.cs @@ -407,10 +407,14 @@ await Task.Run(() => } - // Event handler for the Auto Update Check Toggle Button to modify the User Configurations file + /// + /// Event handler for the Auto Update Check Toggle Button to modify the app settings + /// + /// + /// private void AutoUpdateCheckToggle_Toggled(object sender, RoutedEventArgs e) { - _ = UserConfiguration.Set(AutoUpdateCheck: AutoUpdateCheckToggle.IsOn); + AppSettings.SaveSetting(AppSettings.SettingKeys.AutoCheckForUpdateAtStartup, AutoUpdateCheckToggle.IsOn); } @@ -425,8 +429,8 @@ protected override void OnNavigatedTo(NavigationEventArgs e) // Call the base class implementation first base.OnNavigatedTo(e); - // Set the toggle for Auto Update Check based on the User Configurations - AutoUpdateCheckToggle.IsOn = (UserConfiguration.Get().AutoUpdateCheck == true); + // Set the toggle for Auto Update Check based on app settings + AutoUpdateCheckToggle.IsOn = AppSettings.TryGetSetting(AppSettings.SettingKeys.AutoCheckForUpdateAtStartup) ?? true; // Grab the latest text for the CheckForUpdateButton button CheckForUpdateButton.Content = GlobalVars.updateButtonTextOnTheUpdatePage; @@ -451,9 +455,9 @@ private void HardenedUpdateProcedureToggle_Toggled(object sender, RoutedEventArg /// private void AutoUpdateCheckToggleSettingsCard_Click(object sender, RoutedEventArgs e) { - _ = UserConfiguration.Set(AutoUpdateCheck: AutoUpdateCheckToggle.IsOn); - AutoUpdateCheckToggle.IsOn = !AutoUpdateCheckToggle.IsOn; + + AppSettings.SaveSetting(AppSettings.SettingKeys.AutoCheckForUpdateAtStartup, AutoUpdateCheckToggle.IsOn); }