From 0dec8a74239cff769836cae577fbd84824070e83 Mon Sep 17 00:00:00 2001 From: Roy Date: Sat, 21 Apr 2018 19:49:05 +0300 Subject: Implemented NavigationControl for better performance!!! Redesign of machine studio module initialization. --- Software/DB/Tango.mdf | Bin 75497472 -> 75497472 bytes Software/DB/Tango_log.ldf | Bin 1572864 -> 1572864 bytes .../Tango.MachineStudio.ColorLab/ColorLabModule.cs | 4 +- .../Modules/Tango.MachineStudio.DB/DBModule.cs | 10 +- .../DataCaptureModule.cs | 6 +- .../DeveloperModule.cs | 10 +- .../Navigation/DeveloperNavigationManager.cs | 2 +- .../ViewModels/MainViewVM.cs | 4 + .../Views/MainView.xaml | 18 +- .../HardwareDesignerModule.cs | 7 +- .../Tango.MachineStudio.Logging/LoggingModule.cs | 7 +- .../Navigation/LoggingNavigationManager.cs | 2 +- .../ViewModels/ApplicationLogsViewVM.cs | 9 +- .../ViewModels/EmbeddedLogsViewVM.cs | 9 +- .../Views/MainView.xaml | 26 +- .../MachineDesignerModule.cs | 10 +- .../Tango.MachineStudio.Stubs/StubsModule.cs | 10 +- .../SynchronizationModule.cs | 10 +- .../TechnicianModule.cs | 10 +- .../Navigation/UsersAndRolesNavigationManager.cs | 2 +- .../UsersAndRolesModule.cs | 7 +- .../Views/MainView.xaml | 18 +- .../Views/OrganizationManagementView.xaml.cs | 5 +- .../Views/UserManagementView.xaml.cs | 5 +- .../Tango.MachineStudio.Common/IStudioModule.cs | 4 +- .../IStudioModuleViewVM.cs | 29 ++ .../Tango.MachineStudio.Common/StudioModuleBase.cs | 4 +- .../Tango.MachineStudio.Common.csproj | 1 + .../Tango.MachineStudio.UI/MainWindow.xaml | 26 +- .../Tango.MachineStudio.UI/MainWindow.xaml.cs | 2 +- .../Modules/DefaultStudioModuleLoader.cs | 1 + .../Navigation/DefaultNavigationManager.cs | 2 +- .../SupervisingController/IMainView.cs | 10 +- .../Tango.MachineStudio.UI/ViewModelLocator.cs | 1 + .../ViewModels/LoginViewVM.cs | 21 +- .../ViewModels/MainViewVM.cs | 28 +- .../ViewModels/ModuleWindowVM.cs | 5 +- .../Tango.MachineStudio.UI/Views/LoginView.xaml | 7 +- .../Tango.MachineStudio.UI/Views/LoginView.xaml.cs | 24 +- .../Tango.MachineStudio.UI/Views/MainView.xaml | 134 +++--- .../Tango.MachineStudio.UI/Views/MainView.xaml.cs | 26 +- .../Views/ShutdownView.xaml.cs | 5 +- .../Views/UpdateView.xaml.cs | 5 +- .../Tango.SharedUI/Controls/NavigationControl.cs | 458 +++++++++++++++++++++ .../Tango.SharedUI/Tango.SharedUI.csproj | 1 + 45 files changed, 740 insertions(+), 245 deletions(-) create mode 100644 Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModuleViewVM.cs create mode 100644 Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs (limited to 'Software') diff --git a/Software/DB/Tango.mdf b/Software/DB/Tango.mdf index ca7c73155..eef289bf0 100644 Binary files a/Software/DB/Tango.mdf and b/Software/DB/Tango.mdf differ diff --git a/Software/DB/Tango_log.ldf b/Software/DB/Tango_log.ldf index 0505c5228..3c1d8b87e 100644 Binary files a/Software/DB/Tango_log.ldf and b/Software/DB/Tango_log.ldf differ diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.ColorLab/ColorLabModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.ColorLab/ColorLabModule.cs index 3e63051ee..bdb7b136f 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.ColorLab/ColorLabModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.ColorLab/ColorLabModule.cs @@ -38,11 +38,11 @@ namespace Tango.MachineStudio.ColorLab } } - public override FrameworkElement MainView + public override Type MainViewType { get { - return new MainView(); + return typeof(MainView); } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DB/DBModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DB/DBModule.cs index b53f28bd4..4b2fe4074 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DB/DBModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DB/DBModule.cs @@ -34,9 +34,15 @@ namespace Tango.MachineStudio.DB public override BitmapSource Image => SharedUI.Helpers.ResourceHelper.GetImageFromResources("Images/db.png"); /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public override FrameworkElement MainView => new MainDBView(); + public override Type MainViewType + { + get + { + return typeof(MainDBView); + } + } /// /// Gets the permission required to see and load this module. diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DataCapture/DataCaptureModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DataCapture/DataCaptureModule.cs index 38e82257f..eb463e3c2 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DataCapture/DataCaptureModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.DataCapture/DataCaptureModule.cs @@ -53,13 +53,13 @@ namespace Tango.MachineStudio.DataCapture } /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public override FrameworkElement MainView + public override Type MainViewType { get { - return new MainView(); + return typeof(MainView); } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/DeveloperModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/DeveloperModule.cs index 9ac8de012..166a3212a 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/DeveloperModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/DeveloperModule.cs @@ -35,9 +35,15 @@ namespace Tango.MachineStudio.Developer public override BitmapSource Image => ResourceHelper.GetImageFromResources("Images/developer.jpg"); /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public override FrameworkElement MainView => new MainView(); + public override Type MainViewType + { + get + { + return typeof(MainView); + } + } /// /// Gets the permission required to see and load this module. diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Navigation/DeveloperNavigationManager.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Navigation/DeveloperNavigationManager.cs index e92546b47..ff8b0320d 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Navigation/DeveloperNavigationManager.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Navigation/DeveloperNavigationManager.cs @@ -16,7 +16,7 @@ namespace Tango.MachineStudio.Developer.Navigation public void NavigateTo(DeveloperNavigationView view) { LogManager.Log(String.Format("Navigating to view {0}...", view.ToString())); - MainView.Instance.TransitionControl.AutoNavigate(view.ToString()); + MainView.Instance.TransitionControl.NavigateTo(view.ToString()); } } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/ViewModels/MainViewVM.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/ViewModels/MainViewVM.cs index 036b01e34..377b15610 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/ViewModels/MainViewVM.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/ViewModels/MainViewVM.cs @@ -36,6 +36,8 @@ using System.Media; using Tango.MachineStudio.Common.EventLogging; using Tango.MachineStudio.Common.Speech; using Microsoft.Practices.ServiceLocation; +using System.Threading; +using Tango.SharedUI.Helpers; namespace Tango.MachineStudio.Developer.ViewModels { @@ -1361,7 +1363,9 @@ namespace Tango.MachineStudio.Developer.ViewModels _blockInvalidateCommands = false; InvalidateRelayCommands(); + UIHelper.DoEvents(); _navigation.NavigateTo(DeveloperNavigationView.JobView); + } } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Views/MainView.xaml b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Views/MainView.xaml index c4915a4c8..a3ac2f3b9 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Views/MainView.xaml +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Developer/Views/MainView.xaml @@ -395,19 +395,11 @@ - - - - - - - - - - - - - + + + + + diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.HardwareDesigner/HardwareDesignerModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.HardwareDesigner/HardwareDesignerModule.cs index 71b86b54a..3c4d6e36a 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.HardwareDesigner/HardwareDesignerModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.HardwareDesigner/HardwareDesignerModule.cs @@ -39,11 +39,14 @@ namespace Tango.MachineStudio.HardwareDesigner } } - public override FrameworkElement MainView + /// + /// Gets the module entry point view type. + /// + public override Type MainViewType { get { - return new MainView(); + return typeof(MainView); } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/LoggingModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/LoggingModule.cs index 91a9f51b0..b389c121e 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/LoggingModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/LoggingModule.cs @@ -38,11 +38,14 @@ namespace Tango.MachineStudio.Logging } } - public override FrameworkElement MainView + /// + /// Gets the module entry point view type. + /// + public override Type MainViewType { get { - return new MainView(); + return typeof(MainView); } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Navigation/LoggingNavigationManager.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Navigation/LoggingNavigationManager.cs index b86df7b0f..496baf4c4 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Navigation/LoggingNavigationManager.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Navigation/LoggingNavigationManager.cs @@ -16,7 +16,7 @@ namespace Tango.MachineStudio.Logging.Navigation public void NavigateTo(LoggingNavigationView view) { LogManager.Log(String.Format("Navigating to view {0}...", view.ToString())); - MainView.Instance.TransitionControl.AutoNavigate(view.ToString()); + MainView.Instance.TransitionControl.NavigateTo(view.ToString()); } } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/ApplicationLogsViewVM.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/ApplicationLogsViewVM.cs index d51607004..ffb16fed4 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/ApplicationLogsViewVM.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/ApplicationLogsViewVM.cs @@ -103,10 +103,13 @@ namespace Tango.MachineStudio.Logging.ViewModels IsRealTime = true; RealTimePaused = true; - SelectedDate = Dates.Last(); + SelectedDate = Dates.LastOrDefault(); - MinDate = Dates.Min(); - MaxDate = Dates.Max(); + if (Dates.Count > 0) + { + MinDate = Dates.Min(); + MaxDate = Dates.Max(); + } LogManager.NewLog += LogManager_NewLog; diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/EmbeddedLogsViewVM.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/EmbeddedLogsViewVM.cs index 126f61402..959d294c7 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/EmbeddedLogsViewVM.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/ViewModels/EmbeddedLogsViewVM.cs @@ -105,10 +105,13 @@ namespace Tango.MachineStudio.Logging.ViewModels IsRealTime = true; RealTimePaused = true; - SelectedDate = Dates.Last(); + SelectedDate = Dates.LastOrDefault(); - MinDate = Dates.Min(); - MaxDate = Dates.Max(); + if (Dates.Count > 0) + { + MinDate = Dates.Min(); + MaxDate = Dates.Max(); + } MachineOperator.EmbeddedLogManager.NewLog += EmbeddedLogManager_NewLog; diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Views/MainView.xaml b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Views/MainView.xaml index bf1bc8778..29a563c72 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Views/MainView.xaml +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Logging/Views/MainView.xaml @@ -16,24 +16,12 @@ d:DesignHeight="1080" d:DesignWidth="1920" d:DataContext="{d:DesignInstance Type=vm:EventsViewVM, IsDesignTimeCreatable=False}" DataContext="{x:Static global:ViewModelLocator.EventsViewVM}"> - - - - - - - - - - - - - - - - - - - + + + + + + + diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.MachineDesigner/MachineDesignerModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.MachineDesigner/MachineDesignerModule.cs index c770695c6..9b37303c7 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.MachineDesigner/MachineDesignerModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.MachineDesigner/MachineDesignerModule.cs @@ -35,9 +35,15 @@ namespace Tango.MachineStudio.MachineDesigner public override BitmapSource Image => ResourceHelper.GetImageFromResources("Images/machine-designer-module.jpg"); /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public override FrameworkElement MainView => new MainView(); + public override Type MainViewType + { + get + { + return typeof(MainView); + } + } /// /// Gets the permission required to see and load this module. diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Stubs/StubsModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Stubs/StubsModule.cs index 62a208d87..aa8041669 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Stubs/StubsModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Stubs/StubsModule.cs @@ -35,9 +35,15 @@ namespace Tango.MachineStudio.Stubs public override BitmapSource Image => ResourceHelper.GetImageFromResources("Images/stubs.jpg"); /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public override FrameworkElement MainView => new MainView(); + public override Type MainViewType + { + get + { + return typeof(MainView); + } + } /// /// Gets the permission required to see and load this module. diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Synchronization/SynchronizationModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Synchronization/SynchronizationModule.cs index 1a05c9248..29fc95aec 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Synchronization/SynchronizationModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Synchronization/SynchronizationModule.cs @@ -35,9 +35,15 @@ namespace Tango.MachineStudio.Synchronization public override BitmapSource Image => ResourceHelper.GetImageFromResources("Images/synchronization.jpg"); /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public override FrameworkElement MainView => new MainView(); + public override Type MainViewType + { + get + { + return typeof(MainView); + } + } /// /// Gets the permission required to see and load this module. diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Technician/TechnicianModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Technician/TechnicianModule.cs index 92293e7d0..4ced0fb30 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Technician/TechnicianModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.Technician/TechnicianModule.cs @@ -35,9 +35,15 @@ namespace Tango.MachineStudio.Technician public override BitmapSource Image => ResourceHelper.GetImageFromResources("Images/technician.jpg"); /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public override FrameworkElement MainView => new MachineTechView(); + public override Type MainViewType + { + get + { + return typeof(MachineTechView); + } + } /// /// Gets the permission required to see and load this module. diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Navigation/UsersAndRolesNavigationManager.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Navigation/UsersAndRolesNavigationManager.cs index b335f2d69..b56962df7 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Navigation/UsersAndRolesNavigationManager.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Navigation/UsersAndRolesNavigationManager.cs @@ -16,7 +16,7 @@ namespace Tango.MachineStudio.UsersAndRoles.Navigation public void NavigateTo(UsersAndRolesNavigationView view) { LogManager.Log(String.Format("Navigating to view {0}...", view.ToString())); - MainView.Instance.TransitionControl.AutoNavigate(view.ToString()); + MainView.Instance.TransitionControl.NavigateTo(view.ToString()); } } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/UsersAndRolesModule.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/UsersAndRolesModule.cs index c0d1326cf..ac471db06 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/UsersAndRolesModule.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/UsersAndRolesModule.cs @@ -38,11 +38,14 @@ namespace Tango.MachineStudio.UsersAndRoles } } - public override FrameworkElement MainView + /// + /// Gets the module entry point view type. + /// + public override Type MainViewType { get { - return new MainView(); + return typeof(MainView); } } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/MainView.xaml b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/MainView.xaml index 90166f445..efe58b363 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/MainView.xaml +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/MainView.xaml @@ -11,18 +11,10 @@ mc:Ignorable="d" d:DesignHeight="1080" d:DesignWidth="1920" d:DataContext="{d:DesignInstance Type=vm:MainViewVM, IsDesignTimeCreatable=False}" DataContext="{x:Static global:ViewModelLocator.MainViewVM}"> - - - - - - - - - - - - - + + + + + diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/OrganizationManagementView.xaml.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/OrganizationManagementView.xaml.cs index e2c44a584..b9f513a1e 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/OrganizationManagementView.xaml.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/OrganizationManagementView.xaml.cs @@ -13,20 +13,21 @@ using System.Windows.Media.Imaging; using System.Windows.Navigation; using System.Windows.Shapes; using static Tango.SharedUI.Controls.MultiTransitionControl; +using static Tango.SharedUI.Controls.NavigationControl; namespace Tango.MachineStudio.UsersAndRoles.Views { /// /// Interaction logic for OrganizationManagementView.xaml /// - public partial class OrganizationManagementView : UserControl , ITransitionView + public partial class OrganizationManagementView : UserControl , INavigationView { public OrganizationManagementView() { InitializeComponent(); } - public void OnTransitionCompleted() + public void OnNavigated() { address_auto.Text = ""; } diff --git a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/UserManagementView.xaml.cs b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/UserManagementView.xaml.cs index f2ff25637..d25932403 100644 --- a/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/UserManagementView.xaml.cs +++ b/Software/Visual_Studio/MachineStudio/Modules/Tango.MachineStudio.UsersAndRoles/Views/UserManagementView.xaml.cs @@ -16,13 +16,14 @@ using Tango.BL.Entities; using Tango.DragAndDrop; using Tango.MachineStudio.UsersAndRoles.ViewModels; using static Tango.SharedUI.Controls.MultiTransitionControl; +using static Tango.SharedUI.Controls.NavigationControl; namespace Tango.MachineStudio.UsersAndRoles.Views { /// /// Interaction logic for UserManagementView.xaml /// - public partial class UserManagementView : UserControl, ITransitionView + public partial class UserManagementView : UserControl, INavigationView { private MainViewVM _vm; @@ -49,7 +50,7 @@ namespace Tango.MachineStudio.UsersAndRoles.Views } } - public void OnTransitionCompleted() + public void OnNavigated() { address_auto.Text = ""; } diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModule.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModule.cs index ee01def9e..6963892fa 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModule.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModule.cs @@ -32,9 +32,9 @@ namespace Tango.MachineStudio.Common BitmapSource Image { get; } /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - FrameworkElement MainView { get; } + Type MainViewType { get; } /// /// Gets or sets a value indicating whether this module is shown under a new window. diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModuleViewVM.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModuleViewVM.cs new file mode 100644 index 000000000..1fd562590 --- /dev/null +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/IStudioModuleViewVM.cs @@ -0,0 +1,29 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace Tango.MachineStudio.Common +{ + public interface IStudioModuleViewVM + { + /// + /// Called when the module . + /// + void OnNavigatedTo(); + /// + /// Called when [navigated from]. + /// + void OnNavigatedFrom(); + /// + /// Called when [shutting down]. + /// + void OnShuttingDown(); + /// + /// Called when the application is shutting down. + /// + /// + Task OnShutdownRequest(); + } +} diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/StudioModuleBase.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/StudioModuleBase.cs index 11da53c6c..68fe5b95e 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/StudioModuleBase.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/StudioModuleBase.cs @@ -41,9 +41,9 @@ namespace Tango.MachineStudio.Common public abstract BitmapSource Image { get; } /// - /// Gets the module entry point view. + /// Gets the module entry point view type. /// - public abstract FrameworkElement MainView { get; } + public abstract Type MainViewType { get; } /// /// Gets the permission required to see and load this module. diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/Tango.MachineStudio.Common.csproj b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/Tango.MachineStudio.Common.csproj index bbbab06ab..ab99a3ad7 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/Tango.MachineStudio.Common.csproj +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.Common/Tango.MachineStudio.Common.csproj @@ -107,6 +107,7 @@ + diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml index 6d8d86a8c..1dfe4c18f 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml @@ -17,25 +17,13 @@ - - - - - - - - - - - - - - - - - - - + + + + + + + diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml.cs index 48de019e8..8461a5d93 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/MainWindow.xaml.cs @@ -40,7 +40,7 @@ namespace Tango.MachineStudio.UI Instance = this; ThreadsHelper.SetDisptacher(Dispatcher); - this.Closing += MainWindow_Closing; + this.Closing += MainWindow_Closing; } catch (Exception ex) { diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Modules/DefaultStudioModuleLoader.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Modules/DefaultStudioModuleLoader.cs index 07834393b..d7035b57b 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Modules/DefaultStudioModuleLoader.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Modules/DefaultStudioModuleLoader.cs @@ -109,6 +109,7 @@ namespace Tango.MachineStudio.UI.Modules { LogManager.Log(String.Format("Loading module '{0}'...", moduleType.Name)); var module = Activator.CreateInstance(moduleType) as IStudioModule; + //SimpleIoc.Default.Register(() => module); AllModules.Add(module); } catch (Exception ex) diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Navigation/DefaultNavigationManager.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Navigation/DefaultNavigationManager.cs index 56abbd702..092b958cc 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Navigation/DefaultNavigationManager.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Navigation/DefaultNavigationManager.cs @@ -22,7 +22,7 @@ namespace Tango.MachineStudio.UI.Navigation { MainWindow.Instance.Dispatcher.Invoke(() => { - MainWindow.Instance.TransitionControl.AutoNavigate(view.ToString()); + MainWindow.Instance.TransitionControl.NavigateTo(view.ToString()); }); } } diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/SupervisingController/IMainView.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/SupervisingController/IMainView.cs index fd8ef4be5..b202f61f4 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/SupervisingController/IMainView.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/SupervisingController/IMainView.cs @@ -14,10 +14,10 @@ namespace Tango.MachineStudio.UI.SupervisingController /// public interface IMainView : IView { - /// - /// Navigates to the specified studio module. - /// - /// The module. - void NavigateToModule(IStudioModule module); + ///// + ///// Navigates to the specified studio module. + ///// + ///// The module. + //void NavigateToModule(IStudioModule module); } } diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModelLocator.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModelLocator.cs index 97eb2913b..fa3a38c5c 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModelLocator.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModelLocator.cs @@ -71,6 +71,7 @@ namespace Tango.MachineStudio.UI SimpleIoc.Default.Register(); SimpleIoc.Default.Register(); SimpleIoc.Default.Register(); + SimpleIoc.Default.Register(); SimpleIoc.Default.Register(); SimpleIoc.Default.Register(); SimpleIoc.Default.Register(); diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/LoginViewVM.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/LoginViewVM.cs index 7fefe4a41..fafa752c5 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/LoginViewVM.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/LoginViewVM.cs @@ -41,6 +41,15 @@ namespace Tango.MachineStudio.UI.ViewModels set { _email = value; RaisePropertyChangedAuto(); } } + private String _password; + [Required(ErrorMessage = "Password is required")] + public String Password + { + get { return _password; } + set { _password = value; RaisePropertyChangedAuto(); } + } + + private bool _rememberMe; /// /// Gets or sets a value indicating whether to remember the last user email and password. @@ -54,7 +63,7 @@ namespace Tango.MachineStudio.UI.ViewModels /// /// Gets or sets the login command. /// - public RelayCommand LoginCommand { get; set; } + public RelayCommand LoginCommand { get; set; } /// /// Initializes a new instance of the class. @@ -68,29 +77,29 @@ namespace Tango.MachineStudio.UI.ViewModels _navigationManager = navigationManager; _authenticationProvider = authenticationProvider; _eventLogger = eventLogger; - LoginCommand = new RelayCommand(Login); + LoginCommand = new RelayCommand(Login); cryptographer = new Rfc2898Cryptographer(); Email = SettingsManager.Default.MachineStudio.LastLoginEmail; RememberMe = SettingsManager.Default.MachineStudio.RememberMe; + Password = cryptographer.Decrypt(SettingsManager.Default.MachineStudio.LastLoginPassword); } /// /// Logins the requested user. /// - /// The password. - private void Login(String password) + private void Login() { if (Validate()) { try { - _authenticationProvider.Login(Email, password); + _authenticationProvider.Login(Email, Password); _navigationManager.NavigateTo(NavigationView.MainView); SettingsManager.Default.MachineStudio.LastLoginEmail = Email; SettingsManager.Default.MachineStudio.RememberMe = RememberMe; - SettingsManager.Default.MachineStudio.LastLoginPassword = RememberMe ? cryptographer.Encrypt(password) : null; + SettingsManager.Default.MachineStudio.LastLoginPassword = RememberMe ? cryptographer.Encrypt(Password) : null; SettingsManager.SaveDefaultSettings(); _eventLogger.Log("User logged in"); diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/MainViewVM.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/MainViewVM.cs index 8e451cdce..b97825d34 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/MainViewVM.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/MainViewVM.cs @@ -35,6 +35,7 @@ using Tango.MachineStudio.UI.Windows; using Tango.PMR.Stubs; using Tango.Settings; using Tango.SharedUI; +using Tango.SharedUI.Controls; using Tango.SharedUI.Helpers; using Tango.Transport.Adapters; @@ -497,6 +498,16 @@ namespace Tango.MachineStudio.UI.ViewModels { IsMenuOpened = false; + if (module != null) + { + if (!(MainView.Self as MainView).TransitionControl.Elements.ToList().Exists(x => x.GetType() == module.MainViewType)) + { + FrameworkElement view = Activator.CreateInstance(module.MainViewType) as FrameworkElement; + NavigationControl.SetNavigationName(view, module.Name); + (MainView.Self as MainView).TransitionControl.Elements.Add(view); + } + } + foreach (var m in StudioModuleLoader.AllModules.Where(x => x != module)) { m.IsLoaded = false; @@ -507,12 +518,12 @@ namespace Tango.MachineStudio.UI.ViewModels CurrentModule = module; CurrentModule.IsLoaded = true; IsModuleLoaded = true; - View.NavigateToModule(module); + (MainView.Self as MainView).TransitionControl.NavigateTo(module.Name); } else { IsModuleLoaded = false; - View.NavigateToModule(null); + (MainView.Self as MainView).TransitionControl.NavigateTo("Home"); } } @@ -538,18 +549,21 @@ namespace Tango.MachineStudio.UI.ViewModels module.InNewWindow = true; - var parent = (MainView.Self as MainView).TransitionControl.Controls.SingleOrDefault(x => x.Tag.ToString() == module.Name).Content as Grid; + if (!(MainView.Self as MainView).TransitionControl.Elements.ToList().Exists(x => x.GetType() == module.MainViewType)) + { + FrameworkElement v = Activator.CreateInstance(module.MainViewType) as FrameworkElement; + NavigationControl.SetNavigationName(v, module.Name); + (MainView.Self as MainView).TransitionControl.Elements.Add(v); + } - var view = parent.Children[0] as FrameworkElement; - parent.Children.Remove(view); + var view = (MainView.Self as MainView).TransitionControl.GetAndDetach(module.Name); - ModuleWindowVM vm = new ModuleWindowVM(module, parent); + ModuleWindowVM vm = new ModuleWindowVM(module); ModuleWindow window = new ModuleWindow(this, vm, view); window.Closing += (x, y) => { window.grid.Children.Remove(view); - parent.Children.Add(view); module.InNewWindow = false; }; diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/ModuleWindowVM.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/ModuleWindowVM.cs index a5b737b59..9fd1d68bb 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/ModuleWindowVM.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/ViewModels/ModuleWindowVM.cs @@ -19,11 +19,8 @@ namespace Tango.MachineStudio.UI.ViewModels set { _module = value; RaisePropertyChangedAuto(); } } - public Grid Parent { get; set; } - - public ModuleWindowVM(IStudioModule module, Grid parent) + public ModuleWindowVM(IStudioModule module) { - Parent = parent; Module = module; } } diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml index 84ba597f2..7f54263b7 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml @@ -5,6 +5,7 @@ xmlns:rules="clr-namespace:Tango.MachineStudio.Common.ValidationRules;assembly=Tango.MachineStudio.Common" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:materialDesign="http://materialdesigninxaml.net/winfx/xaml/themes" + xmlns:helpers="clr-namespace:Tango.SharedUI.Helpers;assembly=Tango.SharedUI" xmlns:local="clr-namespace:Tango.MachineStudio.UI.Views" mc:Ignorable="d" d:DesignHeight="720" d:DesignWidth="1280" DataContext="{Binding LoginViewVM, Source={StaticResource Locator}}" Background="Transparent"> @@ -15,7 +16,7 @@ - + @@ -31,10 +32,10 @@ - + Remember me - diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml.cs index 027e37682..bf1dd389d 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/LoginView.xaml.cs @@ -22,26 +22,15 @@ namespace Tango.MachineStudio.UI.Views /// /// Interaction logic for LoginView.xaml /// - public partial class LoginView : UserControl, ITransitionView + public partial class LoginView : UserControl { - private Rfc2898Cryptographer cryptographer; - public LoginView() { InitializeComponent(); - - cryptographer = new Rfc2898Cryptographer(); - } - - public String Password - { - get { return (String)GetValue(PasswordProperty); } - set { SetValue(PasswordProperty, value); } + this.Loaded += LoginView_Loaded; } - public static readonly DependencyProperty PasswordProperty = - DependencyProperty.Register("Password", typeof(String), typeof(LoginView), new PropertyMetadata(null)); - public void OnTransitionCompleted() + private void LoginView_Loaded(object sender, RoutedEventArgs e) { txtEmail.Focus(); @@ -49,13 +38,6 @@ namespace Tango.MachineStudio.UI.Views { txtPass.Focus(); } - - txtPass.Password = cryptographer.Decrypt(SettingsManager.Default.MachineStudio.LastLoginPassword); - } - - private void txtPass_PasswordChanged(object sender, RoutedEventArgs e) - { - Password = txtPass.Password; } } } diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml index a841a72cb..dd3d122b6 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml @@ -38,14 +38,14 @@ - + + IsChecked="{Binding Source={x:Reference MenuToggleButton}, Path=IsChecked, Mode=TwoWay}" /> @@ -330,77 +330,73 @@ - - - - - - - - - - - Welcome to Machine Studio - The below modules are displayed according to your user roles and permissions. - - + + + + + + + + + Welcome to Machine Studio + The below modules are displayed according to your user roles and permissions. + + - - - - - - - - + + + + + + + + - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - + + + + + + + + + + + diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml.cs index 442d11cdd..df1f97f23 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/MainView.xaml.cs @@ -26,6 +26,7 @@ using System.Threading; using Tango.Core.Helpers; using Tango.SharedUI.Helpers; using Tango.Logging; +using static Tango.SharedUI.Controls.NavigationControl; namespace Tango.MachineStudio.UI.Views { @@ -44,15 +45,8 @@ namespace Tango.MachineStudio.UI.Views _loader.ModulesLoaded += Loader_ModulesLoaded; } - public void NavigateToModule(IStudioModule module) - { - TransitionControl.AutoNavigate(module != null ? module.Name : "Home"); - } - private void Loader_ModulesLoaded(object sender, EventArgs e) { - TransitionControl.Controls.RemoveAll((x) => x.Tag.ToString() != "Home"); - Task.Factory.StartNew(() => { LogManager.Default.Log("Loading modules views..."); @@ -74,15 +68,12 @@ namespace Tango.MachineStudio.UI.Views ThreadsHelper.InvokeUI(() => { - Grid grid = new Grid(); - grid.Children.Add(module.MainView); - - TransitionControl.Controls.Add(new ContentControl() + if (!TransitionControl.Elements.ToList().Exists(x => x.GetType() == module.MainViewType)) { - Tag = module.Name, - Content = grid, - Visibility = Visibility.Hidden, - }); + FrameworkElement view = Activator.CreateInstance(module.MainViewType) as FrameworkElement; + NavigationControl.SetNavigationName(view, module.Name); + TransitionControl.Elements.Add(view); + } _loader.UserModules.Add(module); }); @@ -92,11 +83,6 @@ namespace Tango.MachineStudio.UI.Views Thread.Sleep(100); } - ThreadsHelper.InvokeUI(() => - { - TransitionControl.RefreshControls(); - }); - item.Pop(); }); } diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/ShutdownView.xaml.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/ShutdownView.xaml.cs index afe6d3800..e1e16592b 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/ShutdownView.xaml.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/ShutdownView.xaml.cs @@ -13,20 +13,21 @@ using System.Windows.Media.Imaging; using System.Windows.Navigation; using System.Windows.Shapes; using static Tango.SharedUI.Controls.MultiTransitionControl; +using static Tango.SharedUI.Controls.NavigationControl; namespace Tango.MachineStudio.UI.Views { /// /// Interaction logic for ShutdownView.xaml /// - public partial class ShutdownView : UserControl, ITransitionView + public partial class ShutdownView : UserControl, INavigationView { public ShutdownView() { InitializeComponent(); } - public void OnTransitionCompleted() + public void OnNavigated() { progressRing.IsActive = true; } diff --git a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/UpdateView.xaml.cs b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/UpdateView.xaml.cs index 75b74f65d..deb4dfdbe 100644 --- a/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/UpdateView.xaml.cs +++ b/Software/Visual_Studio/MachineStudio/Tango.MachineStudio.UI/Views/UpdateView.xaml.cs @@ -14,13 +14,14 @@ using System.Windows.Navigation; using System.Windows.Shapes; using Tango.MachineStudio.UI.ViewModels; using static Tango.SharedUI.Controls.MultiTransitionControl; +using static Tango.SharedUI.Controls.NavigationControl; namespace Tango.MachineStudio.UI.Views { /// /// Interaction logic for UpdateView.xaml /// - public partial class UpdateView : UserControl, ITransitionView + public partial class UpdateView : UserControl, INavigationView { private UpdateViewVM _vm; @@ -34,7 +35,7 @@ namespace Tango.MachineStudio.UI.Views }; } - public void OnTransitionCompleted() + public void OnNavigated() { _vm.OnNavigatedInto(); } diff --git a/Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs b/Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs new file mode 100644 index 000000000..5a39948b2 --- /dev/null +++ b/Software/Visual_Studio/Tango.SharedUI/Controls/NavigationControl.cs @@ -0,0 +1,458 @@ +using System; +using System.Collections.Generic; +using System.Collections.ObjectModel; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using System.Windows; +using System.Windows.Controls; +using System.Windows.Markup; +using System.Windows.Media; +using System.Windows.Media.Animation; +using Tango.SharedUI.Helpers; + +namespace Tango.SharedUI.Controls +{ + [ContentProperty(nameof(Elements))] + public class NavigationControl : UserControl + { + #region Transition Types + + public enum TransitionTypes + { + Fade, + Zoom, + Slide, + } + + #endregion + + #region Navigation Element + + private class NavigationElement : ContentControl + { + public FrameworkElement Element + { + get { return (FrameworkElement)GetValue(ElementProperty); } + set { SetValue(ElementProperty, value); } + } + public static readonly DependencyProperty ElementProperty = + DependencyProperty.Register("Element", typeof(FrameworkElement), typeof(NavigationControl), new PropertyMetadata(null)); + + public ScaleTransform Scale + { + get { return (ScaleTransform)GetValue(ScaleProperty); } + set { SetValue(ScaleProperty, value); } + } + public static readonly DependencyProperty ScaleProperty = + DependencyProperty.Register("Scale", typeof(ScaleTransform), typeof(NavigationControl), new PropertyMetadata(null)); + + public RotateTransform Rotate + { + get { return (RotateTransform)GetValue(RotateProperty); } + set { SetValue(RotateProperty, value); } + } + public static readonly DependencyProperty RotateProperty = + DependencyProperty.Register("Rotate", typeof(RotateTransform), typeof(NavigationControl), new PropertyMetadata(null)); + + public TranslateTransform Translate + { + get { return (TranslateTransform)GetValue(TranslateProperty); } + set { SetValue(TranslateProperty, value); } + } + public static readonly DependencyProperty TranslateProperty = + DependencyProperty.Register("Translate", typeof(TranslateTransform), typeof(NavigationControl), new PropertyMetadata(null)); + + public NavigationElement() + { + Visibility = Visibility.Hidden; + + Scale = new ScaleTransform(1, 1); + Rotate = new RotateTransform(0); + Translate = new TranslateTransform(0, 0); + + TransformGroup group = new TransformGroup(); + group.Children.Add(Scale); + group.Children.Add(Rotate); + group.Children.Add(Translate); + + RenderTransformOrigin = new Point(0.5, 0.5); + RenderTransform = group; + } + + public NavigationElement(FrameworkElement element) : this() + { + Element = element; + } + + public void AnimateScale(DoubleAnimation animation) + { + Scale.BeginAnimation(ScaleTransform.ScaleXProperty, animation); + Scale.BeginAnimation(ScaleTransform.ScaleYProperty, animation); + } + + public void AnimateTranslateX(DoubleAnimation animation) + { + Translate.BeginAnimation(TranslateTransform.XProperty, animation); + } + + public void AnimateOpacity(DoubleAnimation animation) + { + BeginAnimation(OpacityProperty, animation); + } + + public void Reset() + { + Scale.BeginAnimation(ScaleTransform.ScaleXProperty, null); + Scale.BeginAnimation(ScaleTransform.ScaleYProperty, null); + Rotate.BeginAnimation(RotateTransform.AngleProperty, null); + Translate.BeginAnimation(TranslateTransform.XProperty, null); + Translate.BeginAnimation(TranslateTransform.YProperty, null); + Opacity = 1; + } + + public void Activate() + { + if (Content != Element) + { + Content = Element; + } + + Visibility = Visibility.Visible; + } + + public void Deactivate(bool detach) + { + if (detach) + { + Content = null; + } + + Visibility = Visibility.Hidden; + } + } + + #endregion + + #region INavigationView + + public interface INavigationView + { + void OnNavigated(); + } + + #endregion + + private Grid _grid; + private bool _loaded; + + #region Properties + + public ObservableCollection Elements + { + get { return (ObservableCollection)GetValue(ElementsProperty); } + set { SetValue(ElementsProperty, value); } + } + public static readonly DependencyProperty ElementsProperty = + DependencyProperty.Register("Elements", typeof(ObservableCollection), typeof(NavigationControl), new PropertyMetadata(null, (d, e) => (d as NavigationControl).OnElementsChanged())); + + public FrameworkElement SelectedElement + { + get { return (FrameworkElement)GetValue(SelectedElementProperty); } + set { SetValue(SelectedElementProperty, value); } + } + public static readonly DependencyProperty SelectedElementProperty = + DependencyProperty.Register("SelectedElement", typeof(FrameworkElement), typeof(NavigationControl), new PropertyMetadata(null, (d, e) => (d as NavigationControl).OnSelectedElementChanged(e.OldValue as FrameworkElement, e.NewValue as FrameworkElement))); + + public TransitionTypes TransitionType + { + get { return (TransitionTypes)GetValue(TransitionTypeProperty); } + set { SetValue(TransitionTypeProperty, value); } + } + public static readonly DependencyProperty TransitionTypeProperty = + DependencyProperty.Register("TransitionType", typeof(TransitionTypes), typeof(NavigationControl), new PropertyMetadata(TransitionTypes.Zoom)); + + public bool TransitionAlwaysFades + { + get { return (bool)GetValue(TransitionAlwaysFadesProperty); } + set { SetValue(TransitionAlwaysFadesProperty, value); } + } + public static readonly DependencyProperty TransitionAlwaysFadesProperty = + DependencyProperty.Register("TransitionAlwaysFades", typeof(bool), typeof(NavigationControl), new PropertyMetadata(false)); + + public Duration TransitionDuration + { + get { return (Duration)GetValue(TransitionDurationProperty); } + set { SetValue(TransitionDurationProperty, value); } + } + public static readonly DependencyProperty TransitionDurationProperty = + DependencyProperty.Register("TransitionDuration", typeof(Duration), typeof(NavigationControl), new PropertyMetadata(new Duration(TimeSpan.FromSeconds(0.5)))); + + public bool KeepElementsAttached + { + get { return (bool)GetValue(KeepElementsAttachedProperty); } + set { SetValue(KeepElementsAttachedProperty, value); } + } + public static readonly DependencyProperty KeepElementsAttachedProperty = + DependencyProperty.Register("KeepElementsAttached", typeof(bool), typeof(NavigationControl), new PropertyMetadata(false)); + + + #endregion + + #region Attached Properties + + #region Draggable + + /// + /// Determines the element navigation name. + /// + public static readonly DependencyProperty NavigationName = + DependencyProperty.RegisterAttached("NavigationName", + typeof(String), typeof(NavigationControl), + new FrameworkPropertyMetadata("")); + + /// + /// Sets the name of the navigation. + /// + /// The element. + /// The value. + public static void SetNavigationName(FrameworkElement element, String value) + { + element.SetValue(NavigationName, value); + } + + /// + /// Gets the name of the navigation. + /// + /// The element. + /// + public static String GetNavigationName(FrameworkElement element) + { + return element.GetValue(NavigationName).ToString(); + } + + #endregion + + #endregion + + #region Constructors + + public NavigationControl() + { + ClipToBounds = true; + _grid = new Grid(); + Content = _grid; + Elements = new ObservableCollection(); + Loaded += NavigationControl_Loaded; + } + + #endregion + + #region Event Handlers + + private void NavigationControl_Loaded(object sender, RoutedEventArgs e) + { + if (!_loaded) + { + if (Elements != null) + { + SelectedElement = Elements.FirstOrDefault(); + } + + _loaded = true; + } + } + + private void Elements_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e) + { + SyncElements(); + } + + #endregion + + #region Private Methods + + private void OnElementsChanged() + { + if (Elements != null) + { + Elements.CollectionChanged -= Elements_CollectionChanged; + Elements.CollectionChanged += Elements_CollectionChanged; + } + + SyncElements(); + } + + private void SyncElements() + { + if (Elements == null) + { + _grid.Children.Clear(); + } + else + { + var toRemove = _grid.Children.OfType().ToList().Where(x => !Elements.Contains(x.Element)).ToList(); + var toAdd = Elements.Where(x => !_grid.Children.OfType().Select(y => y.Element).ToList().Contains(x)).ToList(); + + toRemove.ForEach(x => _grid.Children.Remove(x)); + toAdd.ForEach(x => _grid.Children.Add( + new NavigationElement() + { + RenderTransformOrigin = new Point(0.5, 0.5), + Element = x, + Content = KeepElementsAttached ? x : null, + })); + } + + if (!Elements.Contains(SelectedElement)) + { + SelectedElement = null; + } + } + + private NavigationElement GetElementContainer(FrameworkElement element) + { + return _grid.Children.OfType().ToList().SingleOrDefault(x => x.Element == element); + } + + private void Navigate(NavigationElement fromElement, NavigationElement toElement) + { + if (toElement == null) return; + if (toElement == fromElement) return; + + if (fromElement != null) + { + DoubleAnimation toAnimation = new DoubleAnimation(); + toAnimation.Duration = TransitionDuration; + + DoubleAnimation fromAnimation = new DoubleAnimation(); + fromAnimation.Duration = TransitionDuration; + + int fromIndex = Elements.IndexOf(fromElement.Element); + int toIndex = Elements.IndexOf(toElement.Element); + + fromElement.Reset(); + toElement.Reset(); + + fromAnimation.Completed += (_, __) => + { + fromElement.Deactivate(!KeepElementsAttached); + }; + + toAnimation.Completed += (_, __) => + { + INavigationView navigationView = toElement.Element as INavigationView; + if (navigationView != null) + { + navigationView.OnNavigated(); + } + }; + + switch (TransitionType) + { + case TransitionTypes.Fade: + fromAnimation.From = 1; + fromAnimation.To = 0; + + toAnimation.From = 0; + toAnimation.To = 1; + + fromElement.AnimateOpacity(fromAnimation); + toElement.AnimateOpacity(toAnimation); + + break; + case TransitionTypes.Zoom: + fromAnimation.From = 1; + fromAnimation.To = 0; + + toAnimation.From = 0; + toAnimation.To = 1; + + fromElement.AnimateScale(fromAnimation); + toElement.AnimateScale(toAnimation); + + break; + case TransitionTypes.Slide: + + if (toIndex > fromIndex) + { + fromAnimation.From = 0; + fromAnimation.To = -ActualWidth; + + toAnimation.From = ActualWidth; + toAnimation.To = 0; + } + else + { + fromAnimation.From = 0; + fromAnimation.To = ActualWidth; + + toAnimation.From = -ActualWidth; + toAnimation.To = 0; + } + + fromElement.AnimateTranslateX(fromAnimation); + toElement.AnimateTranslateX(toAnimation); + + break; + } + + if (TransitionAlwaysFades && TransitionType != TransitionTypes.Fade) + { + DoubleAnimation fromFadeAnimation = new DoubleAnimation(); + fromFadeAnimation.From = 1; + fromFadeAnimation.To = 0; + fromFadeAnimation.Duration = TransitionDuration; + + DoubleAnimation toFadeAnimation = new DoubleAnimation(); + toFadeAnimation.From = 0; + toFadeAnimation.To = 1; + toFadeAnimation.Duration = TransitionDuration; + + fromElement.AnimateOpacity(fromFadeAnimation); + toElement.AnimateOpacity(toFadeAnimation); + } + + fromElement.Activate(); + toElement.Activate(); + } + else + { + toElement.Activate(); + toElement.Reset(); + } + } + + #endregion + + #region Properties Changes + + protected virtual void OnSelectedElementChanged(FrameworkElement fromElement, FrameworkElement toElement) + { + Navigate(GetElementContainer(fromElement), GetElementContainer(toElement)); + } + + #endregion + + #region Public Methods + + public void NavigateTo(FrameworkElement element) + { + SelectedElement = element; + } + + public void NavigateTo(String navigationName) + { + SelectedElement = Elements.SingleOrDefault(x => GetNavigationName(x) == navigationName); + } + + public FrameworkElement GetAndDetach(String navigationName) + { + var element = Elements.SingleOrDefault(x => GetNavigationName(x) == navigationName); + GetElementContainer(element).Deactivate(!KeepElementsAttached); + return element; + } + + #endregion + } +} diff --git a/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj b/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj index 8ce56b6ff..af4084453 100644 --- a/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj +++ b/Software/Visual_Studio/Tango.SharedUI/Tango.SharedUI.csproj @@ -83,6 +83,7 @@ MultiTransitionControl.xaml + ScriptEditorControl.xaml -- cgit v1.3.1