* Enable Nullable for #4473.

* Fixed bug.

* Fixed indentation bug.

* Fixed line spacing issue.

* Fixed line spacing issue.

* Fixed line spacing issue.
This commit is contained in:
Mike Battista 2022-06-21 09:12:33 -07:00 коммит произвёл GitHub
Родитель 40cfc2e5a3
Коммит 3482afe0ab
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
39 изменённых файлов: 248 добавлений и 165 удалений

Просмотреть файл

@ -2,7 +2,7 @@
public interface ILocalSettingsService
{
Task<T> ReadSettingAsync<T>(string key);
Task<T?> ReadSettingAsync<T>(string key);
Task SaveSettingAsync<T>(string key, T value);
}

Просмотреть файл

@ -23,7 +23,7 @@ public static class SettingsStorageExtensions
await FileIO.WriteTextAsync(file, fileContent);
}
public static async Task<T> ReadAsync<T>(this StorageFolder folder, string name)
public static async Task<T?> ReadAsync<T>(this StorageFolder folder, string name)
{
if (!File.Exists(Path.Combine(folder.Path, GetFileName(name))))
{
@ -46,9 +46,9 @@ public static class SettingsStorageExtensions
settings.Values[key] = value;
}
public static async Task<T> ReadAsync<T>(this ApplicationDataContainer settings, string key)
public static async Task<T?> ReadAsync<T>(this ApplicationDataContainer settings, string key)
{
object obj;
object? obj;
if (settings.Values.TryGetValue(key, out obj))
{
@ -75,7 +75,7 @@ public static class SettingsStorageExtensions
return storageFile;
}
public static async Task<byte[]> ReadFileAsync(this StorageFolder folder, string fileName)
public static async Task<byte[]?> ReadFileAsync(this StorageFolder folder, string fileName)
{
var item = await folder.TryGetItemAsync(fileName).AsTask().ConfigureAwait(false);
@ -89,7 +89,7 @@ public static class SettingsStorageExtensions
return null;
}
public static async Task<byte[]> ReadBytesAsync(this StorageFile file)
public static async Task<byte[]?> ReadBytesAsync(this StorageFile file)
{
if (file != null)
{

Просмотреть файл

@ -2,12 +2,12 @@
public class LocalSettingsOptions
{
public string ApplicationDataFolder
public string? ApplicationDataFolder
{
get; set;
}
public string LocalSettingsFile
public string? LocalSettingsFile
{
get; set;
}

Просмотреть файл

@ -6,7 +6,7 @@ namespace Param_RootNamespace.Services;
public class LocalSettingsServicePackaged : ILocalSettingsService
{
public async Task<T> ReadSettingAsync<T>(string key)
public async Task<T?> ReadSettingAsync<T>(string key)
{
if (ApplicationData.Current.LocalSettings.Values.TryGetValue(key, out var obj))
{

Просмотреть файл

@ -8,35 +8,48 @@ namespace Param_RootNamespace.Services;
public class LocalSettingsServiceUnpackaged : ILocalSettingsService
{
private const string _defaultApplicationDataFolder = "Param_ProjectName/ApplicationData";
private const string _defaultLocalSettingsFile = "LocalSettings.json";
private readonly IFileService _fileService;
private readonly LocalSettingsOptions _options;
private readonly string _localAppData = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
private readonly string _localApplicationData = Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData);
private readonly string _applicationDataFolder;
private readonly string _localsettingsFile;
private IDictionary<string, object> _settings;
private bool _isInitialized;
public LocalSettingsServiceUnpackaged(IFileService fileService, IOptions<LocalSettingsOptions> options)
{
_fileService = fileService;
_options = options.Value;
_applicationDataFolder = Path.Combine(_localApplicationData, _options.ApplicationDataFolder ?? _defaultApplicationDataFolder);
_localsettingsFile = _options.LocalSettingsFile ?? _defaultLocalSettingsFile;
_settings = new Dictionary<string, object>();
}
private async Task InitializeAsync()
{
if (_settings is null)
if (!_isInitialized)
{
var folderPath = Path.Combine(_localAppData, _options.ApplicationDataFolder);
var fileName = _options.LocalSettingsFile;
_settings = await Task.Run(() => _fileService.Read<IDictionary<string, object>>(folderPath, fileName)) ?? new Dictionary<string, object>();
_settings = await Task.Run(() => _fileService.Read<IDictionary<string, object>>(_applicationDataFolder, _localsettingsFile)) ?? new Dictionary<string, object>();
_isInitialized = true;
}
}
public async Task<T> ReadSettingAsync<T>(string key)
public async Task<T?> ReadSettingAsync<T>(string key)
{
await InitializeAsync();
object obj;
object? obj;
if (_settings.TryGetValue(key, out obj))
if (_settings != null && _settings.TryGetValue(key, out obj))
{
return await Json.ToObjectAsync<T>((string)obj);
}
@ -50,8 +63,6 @@ public class LocalSettingsServiceUnpackaged : ILocalSettingsService
_settings[key] = await Json.StringifyAsync(value);
var folderPath = Path.Combine(_localAppData, _options.ApplicationDataFolder);
var fileName = _options.LocalSettingsFile;
await Task.Run(() => _fileService.Save(folderPath, fileName, _settings));
await Task.Run(() => _fileService.Save(_applicationDataFolder, _localsettingsFile, _settings));
}
}

Просмотреть файл

@ -7,9 +7,9 @@ namespace Param_RootNamespace.ViewModels;
public class Param_ItemNameDetailViewModel : ObservableRecipient, INavigationAware
{
private readonly ISampleDataService _sampleDataService;
private SampleOrder _item;
private SampleOrder? _item;
public SampleOrder Item
public SampleOrder? Item
{
get => _item;
set => SetProperty(ref _item, value);

Просмотреть файл

@ -11,9 +11,11 @@ public class Param_ItemNameViewModel : ObservableRecipient, INavigationAware
{
private readonly INavigationService _navigationService;
private readonly ISampleDataService _sampleDataService;
private ICommand _itemClickCommand;
public ICommand ItemClickCommand => _itemClickCommand ??= new RelayCommand<SampleOrder>(OnItemClick);
public ICommand ItemClickCommand
{
get;
}
public ObservableCollection<SampleOrder> Source { get; } = new ObservableCollection<SampleOrder>();
@ -21,6 +23,8 @@ public class Param_ItemNameViewModel : ObservableRecipient, INavigationAware
{
_navigationService = navigationService;
_sampleDataService = sampleDataService;
ItemClickCommand = new RelayCommand<SampleOrder>(OnItemClick);
}
public async void OnNavigatedTo(object parameter)
@ -39,12 +43,12 @@ public class Param_ItemNameViewModel : ObservableRecipient, INavigationAware
{
}
private void OnItemClick(SampleOrder clickedItem)
private void OnItemClick(SampleOrder? clickedItem)
{
if (clickedItem != null)
{
_navigationService.SetListDataItemForNextConnectedAnimation(clickedItem);
_navigationService.NavigateTo(typeof(Param_ItemNameDetailViewModel).FullName, clickedItem.OrderID);
_navigationService.NavigateTo(typeof(Param_ItemNameDetailViewModel).FullName!, clickedItem.OrderID);
}
}
}

Просмотреть файл

@ -24,8 +24,12 @@ public sealed partial class Param_ItemNameDetailPage : Page
base.OnNavigatingFrom(e);
if (e.NavigationMode == NavigationMode.Back)
{
var navigationService = App.GetService<INavigationService>();
navigationService.SetListDataItemForNextConnectedAnimation(ViewModel.Item);
var navigationService = App.GetService<INavigationService>()!;
if (ViewModel.Item != null)
{
navigationService.SetListDataItemForNextConnectedAnimation(ViewModel.Item);
}
}
}
}

Просмотреть файл

@ -9,9 +9,9 @@ namespace Param_RootNamespace.ViewModels;
public class Param_ItemNameViewModel : System.ComponentModel.INotifyPropertyChanged, INavigationAware
{
private readonly ISampleDataService _sampleDataService;
private SampleOrder _selected;
private SampleOrder? _selected;
public SampleOrder Selected
public SampleOrder? Selected
{
get => _selected;
set => SetProperty(ref _selected, value);

Просмотреть файл

@ -6,7 +6,7 @@ namespace Param_RootNamespace.Views;
public sealed partial class Param_ItemNameDetailControl : UserControl
{
public SampleOrder ListDetailsMenuItem
public SampleOrder? ListDetailsMenuItem
{
get => GetValue(ListDetailsMenuItemProperty) as SampleOrder;
set => SetValue(ListDetailsMenuItemProperty, value);
@ -21,7 +21,9 @@ public sealed partial class Param_ItemNameDetailControl : UserControl
private static void OnListDetailsMenuItemPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var control = d as Param_ItemNameDetailControl;
control.ForegroundElement.ChangeView(0, 0, 1);
if (d is Param_ItemNameDetailControl control)
{
control.ForegroundElement.ChangeView(0, 0, 1);
}
}
}

Просмотреть файл

@ -9,6 +9,7 @@ public class Param_ItemNameViewModel : System.ComponentModel.INotifyPropertyChan
{
private readonly IThemeSelectorService _themeSelectorService;
private ElementTheme _elementTheme;
private string _versionDescription;
public ElementTheme ElementTheme
{
@ -16,42 +17,32 @@ public class Param_ItemNameViewModel : System.ComponentModel.INotifyPropertyChan
set => SetProperty(ref _elementTheme, value);
}
private string _versionDescription;
public string VersionDescription
{
get => _versionDescription;
set => SetProperty(ref _versionDescription, value);
}
private ICommand _switchThemeCommand;
public ICommand SwitchThemeCommand
{
get
{
if (_switchThemeCommand == null)
{
_switchThemeCommand = new RelayCommand<ElementTheme>(
async (param) =>
{
if (ElementTheme != param)
{
ElementTheme = param;
await _themeSelectorService.SetThemeAsync(param);
}
});
}
return _switchThemeCommand;
}
get;
}
public Param_ItemNameViewModel(IThemeSelectorService themeSelectorService)
{
_themeSelectorService = themeSelectorService;
_elementTheme = _themeSelectorService.Theme;
VersionDescription = GetVersionDescription();
_versionDescription = GetVersionDescription();
SwitchThemeCommand = new RelayCommand<ElementTheme>(
async (param) =>
{
if (ElementTheme != param)
{
ElementTheme = param;
await _themeSelectorService.SetThemeAsync(param);
}
});
}
private static string GetVersionDescription()

Просмотреть файл

@ -5,6 +5,11 @@ namespace Param_RootNamespace.Contracts.Services;
public interface IWebViewService
{
Uri? Source
{
get;
}
bool CanGoBack
{
get;
@ -15,7 +20,7 @@ public interface IWebViewService
get;
}
event EventHandler<CoreWebView2WebErrorStatus> NavigationCompleted;
event EventHandler<CoreWebView2WebErrorStatus>? NavigationCompleted;
void Initialize(WebView2 webView);

Просмотреть файл

@ -1,4 +1,5 @@
using Microsoft.UI.Xaml.Controls;
using System.Diagnostics.CodeAnalysis;
using Microsoft.UI.Xaml.Controls;
using Microsoft.Web.WebView2.Core;
using Param_RootNamespace.Contracts.Services;
@ -6,31 +7,42 @@ namespace Param_RootNamespace.Services;
public class WebViewService : IWebViewService
{
private WebView2 _webView;
private WebView2? _webView;
public bool CanGoBack => _webView.CanGoBack;
public Uri? Source => _webView?.Source;
public bool CanGoForward => _webView.CanGoForward;
[MemberNotNullWhen(true, nameof(_webView))]
public bool CanGoBack => _webView != null && _webView.CanGoBack;
public event EventHandler<CoreWebView2WebErrorStatus> NavigationCompleted;
[MemberNotNullWhen(true, nameof(_webView))]
public bool CanGoForward => _webView != null && _webView.CanGoForward;
public event EventHandler<CoreWebView2WebErrorStatus>? NavigationCompleted;
public WebViewService()
{
}
[MemberNotNull(nameof(_webView))]
public void Initialize(WebView2 webView)
{
_webView = webView;
_webView.NavigationCompleted += OnWebViewNavigationCompleted;
}
public void GoBack() => _webView.GoBack();
public void GoBack() => _webView?.GoBack();
public void GoForward() => _webView.GoForward();
public void GoForward() => _webView?.GoForward();
public void Reload() => _webView.Reload();
public void Reload() => _webView?.Reload();
public void UnregisterEvents() => _webView.NavigationCompleted -= OnWebViewNavigationCompleted;
public void UnregisterEvents()
{
if (_webView != null)
{
_webView.NavigationCompleted -= OnWebViewNavigationCompleted;
}
}
private void OnWebViewNavigationCompleted(WebView2 sender, CoreWebView2NavigationCompletedEventArgs args) => NavigationCompleted?.Invoke(this, args.WebErrorStatus);
}

Просмотреть файл

@ -12,15 +12,9 @@ namespace Param_RootNamespace.ViewModels;
public class Param_ItemNameViewModel : System.ComponentModel.INotifyPropertyChanged, INavigationAware
{
// TODO: Set the default URL to display.
private const string DefaultUrl = "https://docs.microsoft.com/windows/apps/";
private Uri _source;
private Uri _source = new("https://docs.microsoft.com/windows/apps/");
private bool _isLoading = true;
private bool _hasFailures;
private ICommand _browserBackCommand;
private ICommand _browserForwardCommand;
private ICommand _openInBrowserCommand;
private ICommand _reloadCommand;
private ICommand _retryCommand;
public IWebViewService WebViewService
{
@ -45,30 +39,45 @@ public class Param_ItemNameViewModel : System.ComponentModel.INotifyPropertyChan
set => SetProperty(ref _hasFailures, value);
}
public ICommand BrowserBackCommand => _browserBackCommand ??=
new RelayCommand(() => WebViewService?.GoBack(), () => WebViewService?.CanGoBack ?? false);
public ICommand BrowserBackCommand
{
get;
}
public ICommand BrowserForwardCommand => _browserForwardCommand ??=
new RelayCommand(() => WebViewService?.GoForward(), () => WebViewService?.CanGoForward ?? false);
public ICommand BrowserForwardCommand
{
get;
}
public ICommand ReloadCommand => _reloadCommand ??=
new RelayCommand(() => WebViewService?.Reload());
public ICommand ReloadCommand
{
get;
}
public ICommand RetryCommand => _retryCommand ??=
new RelayCommand(OnRetry);
public ICommand RetryCommand
{
get;
}
public ICommand OpenInBrowserCommand => _openInBrowserCommand ??=
new RelayCommand(async () => await Windows.System.Launcher.LaunchUriAsync(Source));
public ICommand OpenInBrowserCommand
{
get;
}
public Param_ItemNameViewModel(IWebViewService webViewService)
{
WebViewService = webViewService;
BrowserBackCommand = new RelayCommand(() => WebViewService.GoBack(), () => WebViewService.CanGoBack);
BrowserForwardCommand = new RelayCommand(() => WebViewService.GoForward(), () => WebViewService.CanGoForward);
ReloadCommand = new RelayCommand(() => WebViewService.Reload());
RetryCommand = new RelayCommand(OnRetry);
OpenInBrowserCommand = new RelayCommand(async () => await Windows.System.Launcher.LaunchUriAsync(WebViewService.Source), () => WebViewService.Source != null);
}
public void OnNavigatedTo(object parameter)
{
WebViewService.NavigationCompleted += OnNavigationCompleted;
Source = new Uri(DefaultUrl);
}
public void OnNavigatedFrom()
@ -77,7 +86,7 @@ public class Param_ItemNameViewModel : System.ComponentModel.INotifyPropertyChan
WebViewService.NavigationCompleted -= OnNavigationCompleted;
}
private void OnNavigationCompleted(object sender, CoreWebView2WebErrorStatus webErrorStatus)
private void OnNavigationCompleted(object? sender, CoreWebView2WebErrorStatus webErrorStatus)
{
IsLoading = false;
OnPropertyChanged(nameof(BrowserBackCommand));

Просмотреть файл

@ -13,7 +13,7 @@ public sealed partial class Param_ItemNamePage : Page
public Param_ItemNamePage()
{
ViewModel = App.GetService<Param_ItemNameViewModel>();
ViewModel = App.GetService<Param_ItemNameViewModel>()!;
InitializeComponent();
ViewModel.WebViewService.Initialize(WebView);

Просмотреть файл

@ -1,5 +1,4 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>WinExe</OutputType>
<TargetFramework>net6.0-windows10.0.19041.0</TargetFramework>
@ -9,8 +8,9 @@
<Platforms>x86;x64;arm64</Platforms>
<RuntimeIdentifiers>win10-x86;win10-x64;win10-arm64</RuntimeIdentifiers>
<PublishProfile>Properties\PublishProfiles\win10-$(Platform).pubxml</PublishProfile>
<ImplicitUsings>enable</ImplicitUsings>
<UseWinUI>true</UseWinUI>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<UseWinUI>true</UseWinUI>
<EnableMsixTooling>true</EnableMsixTooling>
<WindowsPackageType>None</WindowsPackageType>
</PropertyGroup>

Просмотреть файл

@ -12,17 +12,24 @@ public class Param_ItemNameDetailViewModel : ObservableRecipient, INavigationAwa
//{[{
private readonly INavigationService _navigationService;
//}]}
//^^
//{[{
private ICommand _goBackCommand;
public ICommand GoBackCommand
{
get;
}
public ICommand GoBackCommand => _goBackCommand ??= new RelayCommand(OnGoBack);
//}]}
public Param_ItemNameDetailViewModel(/*{[{*/INavigationService navigationService/*}]}*/)
{
//{[{
_navigationService = navigationService;
//}]}
//^^
//{[{
GoBackCommand = new RelayCommand(OnGoBack);
//}]}
}

Просмотреть файл

@ -16,7 +16,7 @@ public sealed partial class Param_ItemNamePage : Page
public Param_ItemNamePage()
{
//{[{
ViewModel = App.GetService<Param_ItemNameViewModel>();
ViewModel = App.GetService<Param_ItemNameViewModel>()!;
//}]}
}
}

Просмотреть файл

@ -16,7 +16,7 @@ public sealed partial class Param_ItemNameDetailPage : Page
public Param_ItemNameDetailPage()
{
//{[{
ViewModel = App.GetService<Param_ItemNameDetailViewModel>();
ViewModel = App.GetService<Param_ItemNameDetailViewModel>()!;
//}]}
}
}

Просмотреть файл

@ -8,6 +8,6 @@ using System.Reflection;
var appName = "AppDisplayName".GetLocalized();
var version = Assembly.GetExecutingAssembly().GetName().Version;
return $"{appName} - {version.Major}.{version.Minor}.{version.Build}.{version.Revision}";
return $"{appName} - {version?.Major}.{version?.Minor}.{version?.Build}.{version?.Revision}";
//}]}
}

Просмотреть файл

@ -2,18 +2,30 @@
public class ShellViewModel : ObservableRecipient
{
private ICommand _menuFileExitCommand;
public ICommand MenuFileExitCommand
{
get;
}
//{[{
private ICommand _menuParam_ItemNameCommand;
public ICommand MenuParam_ItemNameCommand
{
get;
}
//}]}
public ICommand MenuFileExitCommand => _menuFileExitCommand ??= new RelayCommand(OnMenuFileExit);
//{[{
public ShellViewModel(INavigationService navigationService)
{
NavigationService = navigationService;
NavigationService.Navigated += OnNavigated;
public ICommand MenuParam_ItemNameCommand => _menuParam_ItemNameCommand ??= new RelayCommand(OnMenuParam_ItemName);
MenuFileExitCommand = new RelayCommand(OnMenuFileExit);
//{[{
MenuParam_ItemNameCommand = new RelayCommand(OnMenuParam_ItemName);
//}]}
}
private void OnMenuFileExit() => Application.Current.Exit();
//{[{
private void OnMenuParam_ItemName() => NavigationService.NavigateTo(typeof(Param_ItemNameViewModel).FullName);
private void OnMenuParam_ItemName() => NavigationService.NavigateTo(typeof(Param_ItemNameViewModel).FullName!);
//}]}
}

Просмотреть файл

@ -2,18 +2,30 @@
public class ShellViewModel : ObservableRecipient
{
private ICommand _menuFileExitCommand;
public ICommand MenuFileExitCommand
{
get;
}
//{[{
private ICommand _menuViewsParam_ItemNameCommand;
public ICommand MenuViewsParam_ItemNameCommand
{
get;
}
//}]}
public ICommand MenuFileExitCommand => _menuFileExitCommand ??= new RelayCommand(OnMenuFileExit);
//{[{
public ShellViewModel(INavigationService navigationService)
{
NavigationService = navigationService;
NavigationService.Navigated += OnNavigated;
public ICommand MenuViewsParam_ItemNameCommand => _menuViewsParam_ItemNameCommand ??= new RelayCommand(OnMenuViewsParam_ItemName);
MenuFileExitCommand = new RelayCommand(OnMenuFileExit);
//{[{
MenuViewsParam_ItemNameCommand = new RelayCommand(OnMenuViewsParam_ItemName);
//}]}
}
private void OnMenuFileExit() => Application.Current.Exit();
//{[{
private void OnMenuViewsParam_ItemName() => NavigationService.NavigateTo(typeof(Param_ItemNameViewModel).FullName);
private void OnMenuViewsParam_ItemName() => NavigationService.NavigateTo(typeof(Param_ItemNameViewModel).FullName!);
//}]}
}

Просмотреть файл

@ -11,10 +11,11 @@ namespace Param_RootNamespace.ViewModels;
public class ShellViewModel : ObservableRecipient
{
private bool _isBackEnabled;
private object _selected;
private ICommand _menuFileExitCommand;
public ICommand MenuFileExitCommand => _menuFileExitCommand ??= new RelayCommand(OnMenuFileExit);
public ICommand MenuFileExitCommand
{
get;
}
public INavigationService NavigationService
{
@ -27,16 +28,12 @@ public class ShellViewModel : ObservableRecipient
set => SetProperty(ref _isBackEnabled, value);
}
public object Selected
{
get => _selected;
set => SetProperty(ref _selected, value);
}
public ShellViewModel(INavigationService navigationService)
{
NavigationService = navigationService;
NavigationService.Navigated += OnNavigated;
MenuFileExitCommand = new RelayCommand(OnMenuFileExit);
}
private void OnNavigated(object sender, NavigationEventArgs e) => IsBackEnabled = NavigationService.CanGoBack;

Просмотреть файл

@ -67,7 +67,7 @@ public sealed partial class ShellPage : Page
private static void OnKeyboardAcceleratorInvoked(KeyboardAccelerator sender, KeyboardAcceleratorInvokedEventArgs args)
{
var navigationService = App.GetService<INavigationService>();
var navigationService = App.GetService<INavigationService>()!;
var result = navigationService.GoBack();

Просмотреть файл

@ -11,7 +11,7 @@ public class NavigationViewService : INavigationViewService
// Navigate to the settings page.
//}--}
//{[{
_navigationService.NavigateTo(typeof(Param_ItemNameViewModel).FullName);
_navigationService.NavigateTo(typeof(Param_ItemNameViewModel).FullName!);
//}]}
}
}

Просмотреть файл

@ -8,11 +8,11 @@ namespace Param_RootNamespace.Behaviors;
public class NavigationViewHeaderBehavior : Behavior<NavigationView>
{
private static NavigationViewHeaderBehavior _current;
private static NavigationViewHeaderBehavior? _current;
private Page _currentPage;
private Page? _currentPage;
public DataTemplate DefaultHeaderTemplate
public DataTemplate? DefaultHeaderTemplate
{
get; set;
}
@ -24,48 +24,50 @@ public class NavigationViewHeaderBehavior : Behavior<NavigationView>
}
public static readonly DependencyProperty DefaultHeaderProperty =
DependencyProperty.Register("DefaultHeader", typeof(object), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(null, (d, e) => _current.UpdateHeader()));
DependencyProperty.Register("DefaultHeader", typeof(object), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(null, (d, e) => _current!.UpdateHeader()));
public static NavigationViewHeaderMode GetHeaderMode(Page item) => (NavigationViewHeaderMode)item.GetValue(HeaderModeProperty);
public static void SetHeaderMode(Page item, NavigationViewHeaderMode value) => item.SetValue(HeaderModeProperty, value);
public static readonly DependencyProperty HeaderModeProperty =
DependencyProperty.RegisterAttached("HeaderMode", typeof(bool), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(NavigationViewHeaderMode.Always, (d, e) => _current.UpdateHeader()));
DependencyProperty.RegisterAttached("HeaderMode", typeof(bool), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(NavigationViewHeaderMode.Always, (d, e) => _current!.UpdateHeader()));
public static object GetHeaderContext(Page item) => item.GetValue(HeaderContextProperty);
public static void SetHeaderContext(Page item, object value) => item.SetValue(HeaderContextProperty, value);
public static readonly DependencyProperty HeaderContextProperty =
DependencyProperty.RegisterAttached("HeaderContext", typeof(object), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(null, (d, e) => _current.UpdateHeader()));
DependencyProperty.RegisterAttached("HeaderContext", typeof(object), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(null, (d, e) => _current!.UpdateHeader()));
public static DataTemplate GetHeaderTemplate(Page item) => (DataTemplate)item.GetValue(HeaderTemplateProperty);
public static void SetHeaderTemplate(Page item, DataTemplate value) => item.SetValue(HeaderTemplateProperty, value);
public static readonly DependencyProperty HeaderTemplateProperty =
DependencyProperty.RegisterAttached("HeaderTemplate", typeof(DataTemplate), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(null, (d, e) => _current.UpdateHeaderTemplate()));
DependencyProperty.RegisterAttached("HeaderTemplate", typeof(DataTemplate), typeof(NavigationViewHeaderBehavior), new PropertyMetadata(null, (d, e) => _current!.UpdateHeaderTemplate()));
protected override void OnAttached()
{
base.OnAttached();
_current = this;
var navigationService = App.GetService<INavigationService>();
var navigationService = App.GetService<INavigationService>()!;
navigationService.Navigated += OnNavigated;
_current = this;
}
protected override void OnDetaching()
{
base.OnDetaching();
var navigationService = App.GetService<INavigationService>();
var navigationService = App.GetService<INavigationService>()!;
navigationService.Navigated -= OnNavigated;
}
private void OnNavigated(object sender, NavigationEventArgs e)
{
var frame = sender as Frame;
if (frame.Content is Page page)
if (sender is Frame frame && frame.Content is Page page)
{
_currentPage = page;

Просмотреть файл

@ -4,12 +4,12 @@ namespace Param_RootNamespace.Contracts.Services;
public interface INavigationViewService
{
IList<object> MenuItems
IList<object>? MenuItems
{
get;
}
object SettingsItem
object? SettingsItem
{
get;
}
@ -18,5 +18,5 @@ public interface INavigationViewService
void UnregisterEvents();
NavigationViewItem GetSelectedItem(Type pageType);
NavigationViewItem? GetSelectedItem(Type pageType);
}

Просмотреть файл

@ -7,7 +7,7 @@ public class ActivationService : IActivationService
if (App.MainWindow.Content == null)
{
//{[{
_shell = App.GetService<ShellPage>();
_shell = App.GetService<ShellPage>()!;
//}]}
}
}

Просмотреть файл

@ -1,4 +1,5 @@
using Microsoft.UI.Xaml.Controls;
using System.Diagnostics.CodeAnalysis;
using Microsoft.UI.Xaml.Controls;
using Param_RootNamespace.Contracts.Services;
using Param_RootNamespace.Helpers;
using Param_RootNamespace.ViewModels;
@ -11,11 +12,11 @@ public class NavigationViewService : INavigationViewService
private readonly IPageService _pageService;
private NavigationView _navigationView;
private NavigationView? _navigationView;
public IList<object> MenuItems => _navigationView.MenuItems;
public IList<object>? MenuItems => _navigationView?.MenuItems;
public object SettingsItem => _navigationView.SettingsItem;
public object? SettingsItem => _navigationView?.SettingsItem;
public NavigationViewService(INavigationService navigationService, IPageService pageService)
{
@ -23,6 +24,7 @@ public class NavigationViewService : INavigationViewService
_pageService = pageService;
}
[MemberNotNull(nameof(_navigationView))]
public void Initialize(NavigationView navigationView)
{
_navigationView = navigationView;
@ -32,11 +34,22 @@ public class NavigationViewService : INavigationViewService
public void UnregisterEvents()
{
_navigationView.BackRequested -= OnBackRequested;
_navigationView.ItemInvoked -= OnItemInvoked;
if (_navigationView != null)
{
_navigationView.BackRequested -= OnBackRequested;
_navigationView.ItemInvoked -= OnItemInvoked;
}
}
public NavigationViewItem GetSelectedItem(Type pageType) => GetSelectedItem(_navigationView.MenuItems, pageType);
public NavigationViewItem? GetSelectedItem(Type pageType)
{
if (_navigationView != null)
{
return GetSelectedItem(_navigationView.MenuItems, pageType);
}
return null;
}
private void OnBackRequested(NavigationView sender, NavigationViewBackRequestedEventArgs args) => _navigationService.GoBack();
@ -50,14 +63,14 @@ public class NavigationViewService : INavigationViewService
{
var selectedItem = args.InvokedItemContainer as NavigationViewItem;
if (selectedItem.GetValue(NavigationHelper.NavigateToProperty) is string pageKey)
if (selectedItem?.GetValue(NavigationHelper.NavigateToProperty) is string pageKey)
{
_navigationService.NavigateTo(pageKey);
}
}
}
private NavigationViewItem GetSelectedItem(IEnumerable<object> menuItems, Type pageType)
private NavigationViewItem? GetSelectedItem(IEnumerable<object> menuItems, Type pageType)
{
foreach (var item in menuItems.OfType<NavigationViewItem>())
{

Просмотреть файл

@ -9,7 +9,7 @@ namespace Param_RootNamespace.ViewModels;
public class ShellViewModel : ObservableRecipient
{
private bool _isBackEnabled;
private object _selected;
private object? _selected;
public INavigationService NavigationService
{
@ -27,7 +27,7 @@ public class ShellViewModel : ObservableRecipient
set => SetProperty(ref _isBackEnabled, value);
}
public object Selected
public object? Selected
{
get => _selected;
set => SetProperty(ref _selected, value);

Просмотреть файл

@ -76,7 +76,7 @@ public sealed partial class ShellPage : Page
private static void OnKeyboardAcceleratorInvoked(KeyboardAccelerator sender, KeyboardAcceleratorInvokedEventArgs args)
{
var navigationService = App.GetService<INavigationService>();
var navigationService = App.GetService<INavigationService>()!;
var result = navigationService.GoBack();

Просмотреть файл

@ -11,7 +11,7 @@ public abstract class ActivationHandler<T> : IActivationHandler
// Override this method to add the logic for your activation handler.
protected abstract Task HandleInternalAsync(T args);
public bool CanHandle(object args) => args is T && CanHandleInternal(args as T);
public bool CanHandle(object args) => args is T && CanHandleInternal((args as T)!);
public async Task HandleAsync(object args) => await HandleInternalAsync(args as T);
public async Task HandleAsync(object args) => await HandleInternalAsync((args as T)!);
}

Просмотреть файл

@ -16,12 +16,12 @@ public class DefaultActivationHandler : ActivationHandler<LaunchActivatedEventAr
protected override bool CanHandleInternal(LaunchActivatedEventArgs args)
{
// None of the ActivationHandlers has handled the activation.
return _navigationService.Frame.Content == null;
return _navigationService.Frame?.Content == null;
}
protected async override Task HandleInternalAsync(LaunchActivatedEventArgs args)
{
_navigationService.NavigateTo(typeof(Param_HomeNameViewModel).FullName, args.Arguments);
_navigationService.NavigateTo(typeof(Param_HomeNameViewModel).FullName!, args.Arguments);
await Task.CompletedTask;
}

Просмотреть файл

@ -43,7 +43,7 @@ public partial class App : Application
})
.Build();
public static T GetService<T>()
public static T? GetService<T>()
where T : class
{
return _host.Services.GetService(typeof(T)) as T;
@ -54,7 +54,7 @@ public partial class App : Application
{
//^^
//{[{
var activationService = App.GetService<IActivationService>();
var activationService = App.GetService<IActivationService>()!;
await activationService.ActivateAsync(args);
//}]}
}

Просмотреть файл

@ -12,12 +12,12 @@ public interface INavigationService
get;
}
Frame Frame
Frame? Frame
{
get; set;
}
bool NavigateTo(string pageKey, object parameter = null, bool clearNavigation = false);
bool NavigateTo(string pageKey, object? parameter = null, bool clearNavigation = false);
bool GoBack();
}

Просмотреть файл

@ -4,5 +4,5 @@ namespace Param_RootNamespace.Helpers;
public static class FrameExtensions
{
public static object GetPageViewModel(this Frame frame) => frame?.Content?.GetType().GetProperty("ViewModel")?.GetValue(frame.Content, null);
public static object? GetPageViewModel(this Frame frame) => frame?.Content?.GetType().GetProperty("ViewModel")?.GetValue(frame.Content, null);
}

Просмотреть файл

@ -10,7 +10,7 @@ public class ActivationService : IActivationService
{
private readonly ActivationHandler<LaunchActivatedEventArgs> _defaultHandler;
private readonly IEnumerable<IActivationHandler> _activationHandlers;
private UIElement _shell = null;
private UIElement? _shell = null;
public ActivationService(ActivationHandler<LaunchActivatedEventArgs> defaultHandler, IEnumerable<IActivationHandler> activationHandlers)
{

Просмотреть файл

@ -1,4 +1,5 @@
using Microsoft.UI.Xaml.Controls;
using System.Diagnostics.CodeAnalysis;
using Microsoft.UI.Xaml.Controls;
using Microsoft.UI.Xaml.Navigation;
using Param_RootNamespace.Contracts.Services;
using Param_RootNamespace.Contracts.ViewModels;
@ -11,12 +12,12 @@ namespace Param_RootNamespace.Services;
public class NavigationService : INavigationService
{
private readonly IPageService _pageService;
private object _lastParameterUsed;
private Frame _frame;
private object? _lastParameterUsed;
private Frame? _frame;
public event NavigatedEventHandler Navigated;
public event NavigatedEventHandler? Navigated;
public Frame Frame
public Frame? Frame
{
get
{
@ -37,7 +38,8 @@ public class NavigationService : INavigationService
}
}
public bool CanGoBack => Frame.CanGoBack;
[MemberNotNullWhen(true, nameof(Frame), nameof(_frame))]
public bool CanGoBack => Frame != null && Frame.CanGoBack;
public NavigationService(IPageService pageService)
{
@ -77,11 +79,11 @@ public class NavigationService : INavigationService
return false;
}
public bool NavigateTo(string pageKey, object parameter = null, bool clearNavigation = false)
public bool NavigateTo(string pageKey, object? parameter = null, bool clearNavigation = false)
{
var pageType = _pageService.GetPageType(pageKey);
if (_frame.Content?.GetType() != pageType || (parameter != null && !parameter.Equals(_lastParameterUsed)))
if (_frame != null && (_frame.Content?.GetType() != pageType || (parameter != null && !parameter.Equals(_lastParameterUsed))))
{
_frame.Tag = clearNavigation;
var vmBeforeNavigation = _frame.GetPageViewModel();

Просмотреть файл

@ -16,7 +16,7 @@ public class PageService : IPageService
public Type GetPageType(string key)
{
Type pageType;
Type? pageType;
lock (_pages)
{
if (!_pages.TryGetValue(key, out pageType))
@ -34,7 +34,7 @@ public class PageService : IPageService
{
lock (_pages)
{
var key = typeof(VM).FullName;
var key = typeof(VM).FullName!;
if (_pages.ContainsKey(key))
{
throw new ArgumentException($"The key {key} is already configured in PageService");