diff --git a/Directory.Packages.props b/Directory.Packages.props
index e913b828d..3fde8c6c3 100644
--- a/Directory.Packages.props
+++ b/Directory.Packages.props
@@ -61,14 +61,14 @@
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
diff --git a/e2e/Avalonia/PrismAvaloniaDemo.slnx b/e2e/Avalonia/PrismAvaloniaDemo.slnx
index e572cd053..77bc2e04c 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo.slnx
+++ b/e2e/Avalonia/PrismAvaloniaDemo.slnx
@@ -5,5 +5,11 @@
+
+
+
+
+
+
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/.editorconfig b/e2e/Avalonia/PrismAvaloniaDemo/.editorconfig
index 845700edb..e5108c99b 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/.editorconfig
+++ b/e2e/Avalonia/PrismAvaloniaDemo/.editorconfig
@@ -33,6 +33,7 @@ trim_trailing_whitespace = true
indent_style = space
indent_size = 2
trim_trailing_whitespace = true
+insert_final_newline = true
[*.sln]
indent_size = 2
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/App.axaml.cs b/e2e/Avalonia/PrismAvaloniaDemo/App.axaml.cs
index 19fec496f..6dc883d12 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/App.axaml.cs
+++ b/e2e/Avalonia/PrismAvaloniaDemo/App.axaml.cs
@@ -1,14 +1,10 @@
-using Avalonia;
-using Avalonia.Controls.ApplicationLifetimes;
-using Avalonia.Data.Core;
-using Avalonia.Data.Core.Plugins;
-using Avalonia.Markup.Xaml;
using Prism.DryIoc;
using Prism.Ioc;
using Prism.Navigation.Regions;
using SampleApp.Services;
using SampleApp.ViewModels;
using SampleApp.Views;
+using static Microsoft.IO.RecyclableMemoryStreamManager;
namespace SampleApp;
@@ -20,6 +16,17 @@ public override void Initialize()
// Required when overriding Initialize
base.Initialize();
+
+#if DEBUG
+ // Replaces the old this.AttachDevTools();
+ // NOTE: This requires connection to, http://127.0.0.1:29414/ and some IT firewalls may block it.
+ // Reference: https://docs.avaloniaui.net/tools/developer-tools/attaching-to-the-remote-tool
+ this.AttachDeveloperTools();
+ ////{
+ //// // Change the initialization key gesture (Default is F12)
+ //// options.Gesture = Avalonia.Input.KeyGesture.Parse("F11");
+ ////});
+#endif
}
protected override AvaloniaObject CreateShell()
@@ -29,13 +36,16 @@ protected override AvaloniaObject CreateShell()
protected override void RegisterTypes(IContainerRegistry containerRegistry)
{
- // Register your Services, Views, Dialogs, etc. here
-
// Services
containerRegistry.RegisterSingleton();
+ // Views - Dialogs
+ containerRegistry.RegisterDialog();
+ ////containerRegistry.RegisterDialogWindow(nameof(CustomDialogWindow));
+
// Views - Region Navigation
containerRegistry.RegisterForNavigation();
+ containerRegistry.RegisterForNavigation();
containerRegistry.RegisterForNavigation();
containerRegistry.RegisterForNavigation();
}
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/PrismAvaloniaDemo.csproj b/e2e/Avalonia/PrismAvaloniaDemo/PrismAvaloniaDemo.csproj
index 6c0c67e5d..b3943c324 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/PrismAvaloniaDemo.csproj
+++ b/e2e/Avalonia/PrismAvaloniaDemo/PrismAvaloniaDemo.csproj
@@ -23,8 +23,9 @@
-
-
+
+
+
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/Styles/Icons.axaml b/e2e/Avalonia/PrismAvaloniaDemo/Styles/Icons.axaml
index 36a5d3b89..39d720c42 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/Styles/Icons.axaml
+++ b/e2e/Avalonia/PrismAvaloniaDemo/Styles/Icons.axaml
@@ -1,9 +1,33 @@
-
+
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -13,12 +37,19 @@
- https://avaloniaui.github.io/icons.html
- https://docs.avaloniaui.net/tutorials/music-store-app/add-and-layout-controls
- https://github.com/SKProCH/Material.Icons/blob/master/Material.Icons/MaterialIconDataProvider.PathData.cs
+ - https://www.svgrepo.com/
-->
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/DialogSampleViewModel.cs b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/DialogSampleViewModel.cs
new file mode 100644
index 000000000..3f187112a
--- /dev/null
+++ b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/DialogSampleViewModel.cs
@@ -0,0 +1,46 @@
+using Prism.Commands;
+using Prism.Dialogs;
+using SampleApp.Views;
+
+namespace SampleApp.ViewModels;
+
+public class DialogSampleViewModel : ViewModelBase
+{
+ private readonly IDialogService _dialog;
+
+ private string _msgBoxTitle = string.Empty;
+ private string _msgBoxMessage = string.Empty;
+ private string _msgBoxResult = string.Empty;
+
+ public DialogSampleViewModel(IDialogService dialog)
+ {
+ _dialog = dialog;
+
+ MsgBoxTitle = "Sample Dialog";
+ MsgBoxMessage = "Hello from the DialogSampleViewModel!";
+ Title = "Dialog Sample";
+ }
+
+ public DelegateCommand CmdShowMsgBox => new(() =>
+ {
+ var parameters = new DialogParameters
+ {
+ { "title", MsgBoxTitle },
+ { "message", MsgBoxMessage },
+ };
+
+ _dialog.ShowDialog(nameof(MessageBoxView), parameters, result =>
+ {
+ if (result.Result == ButtonResult.OK)
+ MsgBoxResult = "OK";
+ else if (result.Result == ButtonResult.Cancel)
+ MsgBoxResult = "Cancel";
+ });
+ });
+
+ public string MsgBoxMessage { get => _msgBoxMessage; set => SetProperty(ref _msgBoxMessage, value); }
+
+ public string MsgBoxResult { get => _msgBoxResult; set => SetProperty(ref _msgBoxResult, value); }
+
+ public string MsgBoxTitle { get => _msgBoxTitle; set => SetProperty(ref _msgBoxTitle, value); }
+}
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/MainWindowViewModel.cs b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/MainWindowViewModel.cs
index 92a7af5aa..9053bffd6 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/MainWindowViewModel.cs
+++ b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/MainWindowViewModel.cs
@@ -30,6 +30,11 @@ public MainWindowViewModel(IRegionManager regionManager)
_regionManager.RequestNavigate(RegionNames.ContentRegion, nameof(DashboardView));
});
+ public DelegateCommand CmdDialogSample => new(() =>
+ {
+ _regionManager.RequestNavigate(RegionNames.ContentRegion, nameof(DialogSampleView));
+ });
+
public DelegateCommand CmdFlyoutMenu => new(() =>
{
IsPaneOpened = !IsPaneOpened;
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/MessageBoxViewModel.cs b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/MessageBoxViewModel.cs
new file mode 100644
index 000000000..1344772e2
--- /dev/null
+++ b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/MessageBoxViewModel.cs
@@ -0,0 +1,69 @@
+using System;
+using System.Text;
+using Prism.Commands;
+using Prism.Dialogs;
+using Prism.Mvvm;
+
+namespace SampleApp.ViewModels;
+
+public class MessageBoxViewModel : BindableBase, IDialogAware
+{
+ private string _customMessage = string.Empty;
+ private int _maxHeight;
+ private int _maxWidth;
+ private string _title = "Notification";
+
+ public MessageBoxViewModel()
+ {
+ Title = "Alert!";
+
+ MaxHeight = 800;
+ MaxWidth = 600;
+ }
+
+ public DelegateCommand CmdResult => new DelegateCommand((param) =>
+ {
+ // None = 0
+ // OK = 1
+ // Cancel = 2
+ // Abort = 3
+ // Retry = 4
+ // Ignore = 5
+ // Yes = 6
+ // No = 7
+ ButtonResult result = ButtonResult.None;
+
+ if (int.TryParse(param, out int intResult))
+ result = (ButtonResult)intResult;
+
+ RequestClose.Invoke(result);
+ });
+
+ public string CustomMessage { get => _customMessage; set => SetProperty(ref _customMessage, value); }
+
+ public int MaxHeight { get => _maxHeight; set => SetProperty(ref _maxHeight, value); }
+
+ public int MaxWidth { get => _maxWidth; set => SetProperty(ref _maxWidth, value); }
+
+ public DialogCloseListener RequestClose { get; }
+
+ public string Title { get => _title; set => SetProperty(ref _title, value); }
+
+ /// Allows the dialog to close.
+ /// Return true to allow closing (i.e. OK button only).
+ public virtual bool CanCloseDialog() => true;
+
+ public virtual void OnDialogClosed()
+ {
+ // Detach custom event handlers here, etc.
+ }
+
+ public void OnDialogOpened(IDialogParameters parameters)
+ {
+ var title = parameters.GetValue("title");
+ if (!string.IsNullOrEmpty(title))
+ Title = title;
+
+ CustomMessage = parameters.GetValue("message");
+ }
+}
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/SubSettingsViewModel.cs b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/SubSettingsViewModel.cs
index 939bbe6cf..42ad3c865 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/SubSettingsViewModel.cs
+++ b/e2e/Avalonia/PrismAvaloniaDemo/ViewModels/SubSettingsViewModel.cs
@@ -1,3 +1,5 @@
+using System;
+using System.Collections.Generic;
using Prism.Commands;
using Prism.Navigation.Regions;
using SampleApp.Views;
@@ -6,48 +8,65 @@ namespace SampleApp.ViewModels;
public class SubSettingsViewModel : ViewModelBase
{
- private readonly IRegionManager _regionManager;
- private IRegionNavigationJournal? _journal;
- private string _messageNumber = string.Empty;
- private string _messageText = string.Empty;
-
- public SubSettingsViewModel(IRegionManager regionManager)
- {
- _regionManager = regionManager;
-
- Title = "Settings - SubView";
- }
-
- public DelegateCommand CmdNavigateBack => new DelegateCommand(() =>
- {
- // Go back to the previous calling page, otherwise, Dashboard.
- if (_journal != null && _journal.CanGoBack)
- _journal.GoBack();
- else
- _regionManager.RequestNavigate(RegionNames.ContentRegion, nameof(DashboardView));
- });
-
- public string MessageNumber { get => _messageNumber; set => SetProperty(ref _messageNumber, value); }
-
- public string MessageText { get => _messageText; set => SetProperty(ref _messageText, value); }
-
- /// Navigation completed successfully.
- /// Navigation context.
- public override void OnNavigatedTo(NavigationContext navigationContext)
- {
- // Used to "Go Back" to parent
- _journal = navigationContext.NavigationService.Journal;
-
- // Display our parameters
- MessageText = navigationContext.Parameters["key1"].ToString() ?? "";
- MessageNumber = navigationContext.Parameters["key2"].ToString() ?? "";
- }
-
- public override bool OnNavigatingTo(NavigationContext navigationContext)
- {
- // Navigation permission sample:
- // Don't allow navigation if our keys are missing
- return navigationContext.Parameters.ContainsKey("key1") &&
- navigationContext.Parameters.ContainsKey("key2");
- }
+ private readonly IRegionManager _regionManager;
+ private IRegionNavigationJournal? _journal;
+ private string _messageNumber = string.Empty;
+ private string _messageText = string.Empty;
+
+ public SubSettingsViewModel(IRegionManager regionManager)
+ {
+ _regionManager = regionManager;
+
+ Title = "Settings - SubView";
+ }
+
+ public DelegateCommand CmdNavigateBack => new DelegateCommand(() =>
+ {
+ // Go back to the previous calling page, otherwise, Dashboard.
+ if (_journal != null && _journal.CanGoBack)
+ _journal.GoBack();
+ else
+ _regionManager.RequestNavigate(RegionNames.ContentRegion, nameof(DashboardView));
+ });
+
+ public string MessageNumber { get => _messageNumber; set => SetProperty(ref _messageNumber, value); }
+
+ public string MessageText { get => _messageText; set => SetProperty(ref _messageText, value); }
+
+ /// Navigation completed successfully.
+ /// Navigation context.
+ public override void OnNavigatedTo(NavigationContext navigationContext)
+ {
+ // Used to "Go Back" to parent
+ _journal = navigationContext.NavigationService.Journal;
+
+ // Display our parameters
+ MessageText = GetKeyValueAsString(navigationContext, "key1");
+ MessageNumber = GetKeyValueAsString(navigationContext, "key2");
+
+ }
+
+ public override bool OnNavigatingTo(NavigationContext navigationContext)
+ {
+ // Navigation permission sample:
+ // Don't allow navigation if our keys are missing
+ return navigationContext.Parameters.ContainsKey("key1") &&
+ navigationContext.Parameters.ContainsKey("key2");
+ }
+
+ public static string GetKeyValueAsString(NavigationContext context, string targetKey, string defaultValue = "")
+ {
+ var searchList = context.Parameters;
+ if (searchList == null || targetKey == null)
+ return defaultValue;
+
+ foreach (KeyValuePair kvp in searchList)
+ {
+ // Safe string comparison (Ordinal ignores regional culture bugs)
+ if (string.Equals(kvp.Key, targetKey, StringComparison.Ordinal))
+ return kvp.Value?.ToString() ?? defaultValue;
+ }
+
+ return defaultValue;
+ }
}
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/Views/DashboardView.axaml b/e2e/Avalonia/PrismAvaloniaDemo/Views/DashboardView.axaml
index d9b8271ee..6979051a0 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/Views/DashboardView.axaml
+++ b/e2e/Avalonia/PrismAvaloniaDemo/Views/DashboardView.axaml
@@ -8,7 +8,9 @@
x:Class="SampleApp.Views.DashboardView"
x:CompileBindings="True"
x:DataType="vm:DashboardViewModel"
- d:DesignHeight="350" d:DesignWidth="500" mc:Ignorable="d">
+ d:DesignHeight="350"
+ d:DesignWidth="500"
+ mc:Ignorable="d">
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/Views/MessageBoxView.axaml.cs b/e2e/Avalonia/PrismAvaloniaDemo/Views/MessageBoxView.axaml.cs
new file mode 100644
index 000000000..4a37d1a3b
--- /dev/null
+++ b/e2e/Avalonia/PrismAvaloniaDemo/Views/MessageBoxView.axaml.cs
@@ -0,0 +1,19 @@
+using Avalonia;
+using Avalonia.Controls;
+using Avalonia.Markup.Xaml;
+
+namespace SampleApp.Views;
+
+/// MessageBox Dialog View.
+public partial class MessageBoxView : UserControl
+{
+ public MessageBoxView()
+ {
+ InitializeComponent();
+ }
+
+ private void InitializeComponent()
+ {
+ AvaloniaXamlLoader.Load(this);
+ }
+}
diff --git a/e2e/Avalonia/PrismAvaloniaDemo/Views/SubSettingsView.axaml.cs b/e2e/Avalonia/PrismAvaloniaDemo/Views/SubSettingsView.axaml.cs
index aa5c7558d..d3e474446 100644
--- a/e2e/Avalonia/PrismAvaloniaDemo/Views/SubSettingsView.axaml.cs
+++ b/e2e/Avalonia/PrismAvaloniaDemo/Views/SubSettingsView.axaml.cs
@@ -4,8 +4,8 @@ namespace SampleApp.Views;
public partial class SubSettingsView : UserControl
{
- public SubSettingsView()
- {
- InitializeComponent();
- }
+ public SubSettingsView()
+ {
+ InitializeComponent();
+ }
}
diff --git a/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml b/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml
index ee77baa2d..fc5cd4097 100644
--- a/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml
+++ b/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml
@@ -3,6 +3,7 @@
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
x:Class="Prism.Dialogs.DialogWindow"
+ x:CompileBindings="False"
Title="{Binding Title}"
WindowStartupLocation="CenterOwner">
diff --git a/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml.cs b/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml.cs
index e486c41d2..a4739795a 100644
--- a/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml.cs
+++ b/src/Avalonia/Prism.Avalonia/Dialogs/DialogWindow.axaml.cs
@@ -15,10 +15,6 @@ public partial class DialogWindow : Window, IDialogWindow
public DialogWindow()
{
InitializeComponent();
-
-#if DEBUG
- //// this.AttachDevTools();
-#endif
}
private void InitializeComponent()
diff --git a/src/Avalonia/Prism.Avalonia/Prism.Avalonia.csproj b/src/Avalonia/Prism.Avalonia/Prism.Avalonia.csproj
index 811fccfcb..1cd6e7176 100644
--- a/src/Avalonia/Prism.Avalonia/Prism.Avalonia.csproj
+++ b/src/Avalonia/Prism.Avalonia/Prism.Avalonia.csproj
@@ -51,10 +51,6 @@ Prism.Avalonia helps you more easily design and build rich, flexible, and easy t
-->
-
-
-
-
True
diff --git a/src/Wpf/Prism.Wpf/Navigation/Regions/Behaviors/DelayedRegionCreationBehavior.cs b/src/Wpf/Prism.Wpf/Navigation/Regions/Behaviors/DelayedRegionCreationBehavior.cs
index 535ef7c9c..a83c6ada3 100644
--- a/src/Wpf/Prism.Wpf/Navigation/Regions/Behaviors/DelayedRegionCreationBehavior.cs
+++ b/src/Wpf/Prism.Wpf/Navigation/Regions/Behaviors/DelayedRegionCreationBehavior.cs
@@ -1,9 +1,6 @@
using System.Collections.ObjectModel;
using System.Globalization;
using Prism.Properties;
-#if AVALONIA
-using Avalonia.Threading;
-#endif
namespace Prism.Navigation.Regions.Behaviors
{
@@ -97,11 +94,7 @@ private void TryCreateRegion()
return;
}
-#if !AVALONIA
if (targetElement.CheckAccess())
-#else
- if (Dispatcher.UIThread.CheckAccess())
-#endif
{
Detach();