diff options
| author | Roy Ben Shabat <Roy.mail.net@gmail.com> | 2020-12-18 05:26:29 +0200 |
|---|---|---|
| committer | Roy Ben Shabat <Roy.mail.net@gmail.com> | 2020-12-18 05:26:29 +0200 |
| commit | 86bbaee1a545f08dc7bfb4efe5f4696d6e4dccdd (patch) | |
| tree | 0b46af20d6bb4568e44148b5e89d31da298c43fc /Software/Visual_Studio/StubsUtils | |
| parent | d9ee0b8e11f15c2b3bae068767516bc84a5ca4ed (diff) | |
| download | Tango-86bbaee1a545f08dc7bfb4efe5f4696d6e4dccdd.tar.gz Tango-86bbaee1a545f08dc7bfb4efe5f4696d6e4dccdd.zip | |
StubUtils
Diffstat (limited to 'Software/Visual_Studio/StubsUtils')
16 files changed, 509 insertions, 112 deletions
diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Program.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Program.cs index 9fd588906..4c93c2196 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Program.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Program.cs @@ -1,5 +1,4 @@ -using Newtonsoft.Json; -using System; +using System; using System.Collections.Generic; using System.Diagnostics; using System.IO; @@ -23,7 +22,7 @@ namespace Tango.StubsUtils.Client.CLI try { var _client = new NamedPipeClientStream(PIPE_NAME); - _client.Connect(5000); + _client.Connect(1000); var writer = new StreamWriter(_client); @@ -40,7 +39,7 @@ namespace Tango.StubsUtils.Client.CLI } catch (Exception ex) { - ExitError($"Error communicating with the stubs service. {ex.Message}"); + ExitError($"Status: Error\nError: Error communicating with the stubs service. {ex.Message}"); } if (response.Status == StubPackageResponseStatus.OK) diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Tango.StubsUtils.Client.CLI.csproj b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Tango.StubsUtils.Client.CLI.csproj index 7bbf4b387..8de8ccb89 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Tango.StubsUtils.Client.CLI.csproj +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/Tango.StubsUtils.Client.CLI.csproj @@ -33,9 +33,6 @@ <WarningLevel>4</WarningLevel> </PropertyGroup> <ItemGroup> - <Reference Include="Newtonsoft.Json, Version=9.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL"> - <HintPath>..\..\packages\Newtonsoft.Json.9.0.1\lib\net45\Newtonsoft.Json.dll</HintPath> - </Reference> <Reference Include="System" /> <Reference Include="System.Core" /> <Reference Include="System.Xml.Linq" /> @@ -51,7 +48,6 @@ </ItemGroup> <ItemGroup> <None Include="App.config" /> - <None Include="packages.config" /> </ItemGroup> <ItemGroup> <ProjectReference Include="..\Tango.StubsUtils.Shared\Tango.StubsUtils.Shared.csproj"> diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/packages.config b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/packages.config deleted file mode 100644 index 7ee8c1052..000000000 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Client.CLI/packages.config +++ /dev/null @@ -1,4 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<packages> - <package id="Newtonsoft.Json" version="9.0.1" targetFramework="net461" /> -</packages>
\ No newline at end of file diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.PerformanceTest.CLI/Program.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.PerformanceTest.CLI/Program.cs index 3083037f8..ff172737a 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.PerformanceTest.CLI/Program.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.PerformanceTest.CLI/Program.cs @@ -10,10 +10,63 @@ namespace Tango.StubsUtils.PerformanceTest.CLI { class Program { - private const int ROUNDS = 10000; + private const int ROUNDS = 100; + private const int DELAY = 0; static void Main(string[] args) { + PerformanceTestStandard(); + Console.WriteLine(); + PerformanceTestSession(); + + Console.WriteLine(); + Console.WriteLine(); + Console.WriteLine("Completed."); + Console.ReadLine(); + } + + private static void PerformanceTestStandard() + { + List<double> durations = new List<double>(); + + Stopwatch watch = new Stopwatch(); + + for (int i = 0; i < ROUNDS; i++) + { + watch.Restart(); + + Process process = new Process(); + process.StartInfo.FileName = "tangostub.exe"; + process.StartInfo.CreateNoWindow = true; + process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden; + process.StartInfo.Arguments = "calculate 10 15"; + process.StartInfo.RedirectStandardOutput = true; + process.StartInfo.UseShellExecute = false; + process.Start(); + process.WaitForExit(); + + String response = process.StandardOutput.ReadToEnd(); + + if (!response.StartsWith("Status: OK")) + { + OnError(response); + return; + } + + if (DELAY > 0) + { + Thread.Sleep(DELAY); + } + + durations.Add(watch.ElapsedMilliseconds); + + Console.SetCursorPosition(0, 0); + Console.Write($"Performance Test (Standard): {i + 1}/{ROUNDS}, Avg: {Math.Round(durations.Average(), 2)} ms "); + } + } + + private static void PerformanceTestSession() + { List<double> durations = new List<double>(); Process process = new Process(); @@ -21,7 +74,6 @@ namespace Tango.StubsUtils.PerformanceTest.CLI process.StartInfo.CreateNoWindow = true; process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden; process.StartInfo.RedirectStandardOutput = true; - process.StartInfo.RedirectStandardOutput = true; process.StartInfo.RedirectStandardInput = true; process.StartInfo.UseShellExecute = false; process.Start(); @@ -61,22 +113,22 @@ namespace Tango.StubsUtils.PerformanceTest.CLI String response = builder.ToString(); - if (response.StartsWith("Status: Error")) + if (!response.StartsWith("Status: OK")) { OnError(response); return; } + if (DELAY > 0) + { + Thread.Sleep(DELAY); + } + durations.Add(watch.ElapsedMilliseconds); - Console.SetCursorPosition(0, 0); - Console.Write($"Performance Test: {i + 1}/{ROUNDS}, Avg: {Math.Round(durations.Average(), 2)} ms "); + Console.SetCursorPosition(0, 1); + Console.Write($"Performance Test (Session) : {i + 1}/{ROUNDS}, Avg: {Math.Round(durations.Average(), 2)} ms "); } - - Console.WriteLine(); - Console.WriteLine(); - Console.WriteLine("Completed."); - Console.ReadLine(); } private static void OnError(String error) diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/App.xaml b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/App.xaml index 4db18888a..4b1b7cc93 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/App.xaml +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/App.xaml @@ -62,6 +62,7 @@ <ResourceDictionary Source="/Resources/Converters.xaml" /> <ResourceDictionary Source="/Resources/Colors.xaml" /> <ResourceDictionary Source="/Resources/Fonts.xaml" /> + <ResourceDictionary Source="/Resources/Styles.xaml" /> <ResourceDictionary> <!--OVERRIDE MAHAPPS--> diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Controls/ScrollableFlowDocumentScrollViewer.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Controls/ScrollableFlowDocumentScrollViewer.cs new file mode 100644 index 000000000..5fa00a4ac --- /dev/null +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Controls/ScrollableFlowDocumentScrollViewer.cs @@ -0,0 +1,46 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using System.Windows; +using System.Windows.Controls; +using System.Windows.Media; + +namespace Tango.StubsUtils.Service.UI.Controls +{ + public class ScrollableFlowDocumentScrollViewer : FlowDocumentScrollViewer + { + /// <summary> + /// Backing store for the <see cref="ScrollViewer"/> property. + /// </summary> + private ScrollViewer scrollViewer; + + /// <summary> + /// Gets the scroll viewer contained within the FlowDocumentScrollViewer control + /// </summary> + public ScrollViewer ScrollViewer + { + get + { + if (this.scrollViewer == null) + { + DependencyObject obj = this; + + do + { + if (VisualTreeHelper.GetChildrenCount(obj) > 0) + obj = VisualTreeHelper.GetChild(obj as Visual, 0); + else + return null; + } + while (!(obj is ScrollViewer)); + + this.scrollViewer = obj as ScrollViewer; + } + + return this.scrollViewer; + } + } + } +} diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Resources/Styles.xaml b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Resources/Styles.xaml new file mode 100644 index 000000000..e47e4594c --- /dev/null +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Resources/Styles.xaml @@ -0,0 +1,16 @@ +<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" + xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" + xmlns:material="http://materialdesigninxaml.net/winfx/xaml/themes" + xmlns:local="clr-namespace:Tango.StubsUtils.Service.UI.Resources"> + + <Style x:Key="FSE_RaisedButton_Dark_Hover" TargetType="Button" BasedOn="{StaticResource MaterialDesignRaisedLightButton}"> + <Setter Property="FocusVisualStyle" Value="{x:Null}"></Setter> + <Setter Property="Height" Value="Auto"></Setter> + <Style.Triggers> + <Trigger Property="IsMouseOver" Value="True"> + <Setter Property="Background" Value="{StaticResource FSE_PrimaryBackgroundLighterBrush}"></Setter> + </Trigger> + </Style.Triggers> + </Style> + +</ResourceDictionary>
\ No newline at end of file diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ServiceUISettings.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ServiceUISettings.cs index 92f7157ca..5e4d8209d 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ServiceUISettings.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ServiceUISettings.cs @@ -9,5 +9,12 @@ namespace Tango.StubsUtils.Service.UI { public class ServiceUISettings : SettingsBase { + public String USBPort { get; set; } + public bool AutoConnect { get; set; } + + public ServiceUISettings() + { + USBPort = "COM1"; + } } } diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Tango.StubsUtils.Service.UI.csproj b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Tango.StubsUtils.Service.UI.csproj index c4cdbab42..a4c59bef2 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Tango.StubsUtils.Service.UI.csproj +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Tango.StubsUtils.Service.UI.csproj @@ -78,6 +78,7 @@ <Generator>MSBuild:Compile</Generator> <SubType>Designer</SubType> </ApplicationDefinition> + <Compile Include="Controls\ScrollableFlowDocumentScrollViewer.cs" /> <Compile Include="ServiceUISettings.cs" /> <Compile Include="ViewModels\MainViewVM.cs" /> <Compile Include="Views\MainView.xaml.cs"> @@ -107,6 +108,10 @@ <Generator>MSBuild:Compile</Generator> <SubType>Designer</SubType> </Page> + <Page Include="Resources\Styles.xaml"> + <SubType>Designer</SubType> + <Generator>MSBuild:Compile</Generator> + </Page> <Page Include="Views\MainView.xaml"> <SubType>Designer</SubType> <Generator>MSBuild:Compile</Generator> diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ViewModels/MainViewVM.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ViewModels/MainViewVM.cs index 4e8b144e5..21a183d8a 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ViewModels/MainViewVM.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/ViewModels/MainViewVM.cs @@ -1,17 +1,36 @@ using System; using System.Collections.Generic; +using System.IO.Ports; using System.Linq; using System.Text; +using System.Threading; using System.Threading.Tasks; using System.Windows; +using System.Windows.Documents; +using System.Windows.Input; +using Tango.Core; using Tango.Core.Commands; +using Tango.Logging; +using Tango.Settings; using Tango.SharedUI; +using Tango.SharedUI.Components; using Tango.SharedUI.Helpers; +using Tango.StubsUtils.Service.UI.Views; namespace Tango.StubsUtils.Service.UI.ViewModels { public class MainViewVM : ViewModel { + private ProducerConsumerQueue<String> _logsQueue; + private Thread _logsThread; + + private ServiceUISettings _settings; + public ServiceUISettings Settings + { + get { return _settings; } + set { _settings = value; RaisePropertyChangedAuto(); } + } + private StubsService _service; public StubsService Service { @@ -26,25 +45,131 @@ namespace Tango.StubsUtils.Service.UI.ViewModels set { _isTrayIconVisible = value; RaisePropertyChangedAuto(); } } + private List<String> _availablePorts; + public List<String> AvailablePorts + { + get { return _availablePorts; } + set { _availablePorts = value; RaisePropertyChangedAuto(); } + } + + private String _selectedPort; + public String SelectedPort + { + get { return _selectedPort; } + set { _selectedPort = value; RaisePropertyChangedAuto(); } + } + + private SimpleStringLogger _logger; + public SimpleStringLogger Logger + { + get { return _logger; } + set { _logger = value; RaisePropertyChangedAuto(); } + } public RelayCommand ExitCommand { get; set; } public RelayCommand OpenCommand { get; set; } + public RelayCommand RefreshPortsCommand { get; set; } + public RelayCommand ToggleConnectionCommand { get; set; } + public RelayCommand ClearLogCommand { get; set; } public MainViewVM() { - Init(); ExitCommand = new RelayCommand(ExitApplication); OpenCommand = new RelayCommand(OpenMainWindow); IsTrayIconVisible = true; + AvailablePorts = new List<string>(); + RefreshPortsCommand = new RelayCommand(RefreshPorts); + ToggleConnectionCommand = new RelayCommand(ToggleConnection); + ClearLogCommand = new RelayCommand(ClearLog); + _logsQueue = new ProducerConsumerQueue<string>(); + + _logsThread = new Thread(LogsThreadMethod); + _logsThread.IsBackground = true; + _logsThread.Start(); + + Init(); } public async void Init() { - Service = new StubsService(); - await Service.Start(); + try + { + Logger = new SimpleStringLogger() { Enabled = true }; + Logger.LogReceived += Logger_LogReceived; + + LogManager.RegisterLogger(Logger); + + LogManager.Log("Initializing..."); + Settings = SettingsManager.Default.GetOrCreate<ServiceUISettings>(); + SelectedPort = Settings.USBPort; + + RefreshPorts(); + + Service = new StubsService(); + await Service.Start(); + + if (Settings.AutoConnect) + { + await Task.Delay(2000); + ToggleConnection(); + } + } + catch (Exception ex) + { + LogManager.Log(ex, "Error initializing service."); + } + } + + private void Logger_LogReceived(object sender, LogItemBase e) + { + String message = e.TimeStamp.ToString("HH:mm:ss.ff") + ": " + e.Message; + _logsQueue.BlockEnqueue(message); + } + + private void LogsThreadMethod() + { + while (true) + { + List<String> logs = new List<string>(); + + logs.Add(_logsQueue.BlockDequeue()); + + while (_logsQueue.Count > 0) + { + logs.Add(_logsQueue.BlockDequeue()); + } + + InvokeUINow(() => + { + List<Inline> inlines = new List<Inline>(); - await Task.Delay(10000); - await Service.Connect(); + foreach (var log in logs) + { + inlines.Add(new Run(log)); + inlines.Add(new LineBreak()); + } + + MainView.Instance.paragraphLog.Inlines.AddRange(inlines); + + if (Mouse.LeftButton != MouseButtonState.Pressed) + { + MainView.Instance.scrollViewerLogs.ScrollViewer?.ScrollToEnd(); + } + }); + + Thread.Sleep(200); + } + } + + private void ClearLog() + { + InvokeUI(() => + { + IsFree = false; + UIHelper.DoEvents(); + MainView.Instance.paragraphLog.Inlines.Clear(); + IsFree = true; + }); } private async void OpenMainWindow() @@ -59,10 +184,67 @@ namespace Tango.StubsUtils.Service.UI.ViewModels public async void ExitApplication() { + IsFree = false; + SaveSettings(); IsTrayIconVisible = false; UIHelper.DoEvents(); await Task.Delay(1000); Environment.Exit(0); } + + private void RefreshPorts() + { + AvailablePorts = SerialPort.GetPortNames().ToList(); + + if (!AvailablePorts.Contains(SelectedPort)) + { + SelectedPort = AvailablePorts.FirstOrDefault(); + } + + InvalidateRelayCommands(); + } + + private async void ToggleConnection() + { + try + { + IsFree = false; + + if (!Service.IsConnected) + { + try + { + await Service.Connect(SelectedPort); + SaveSettings(); + //ToastNotificationManager.CreateToastNotifier("MyApplicationId").Show(toast); + } + catch (Exception ex) + { + LogManager.Log(ex, "Error connecting to the specified serial port."); + } + } + else + { + try + { + await Service.Disconnect(); + } + catch (Exception ex) + { + LogManager.Log(ex, "Error disconnecting from the specified serial port."); + } + } + } + finally + { + IsFree = true; + } + } + + private void SaveSettings() + { + Settings.USBPort = SelectedPort; + Settings.Save(); + } } } diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml index eb2c24e44..7cb2e1413 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml @@ -5,10 +5,11 @@ xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:tb="http://www.hardcodet.net/taskbar" xmlns:material="http://materialdesigninxaml.net/winfx/xaml/themes" + xmlns:controls="clr-namespace:Tango.StubsUtils.Service.UI.Controls" xmlns:local="clr-namespace:Tango.StubsUtils.Service.UI.Views" xmlns:vm="clr-namespace:Tango.StubsUtils.Service.UI.ViewModels" mc:Ignorable="d" - d:DesignHeight="450" d:DesignWidth="800" Background="{StaticResource FSE_PrimaryBackgroundBrush}" d:DataContext="{d:DesignInstance Type=vm:MainViewVM,IsDesignTimeCreatable=False}"> + d:DesignHeight="400" d:DesignWidth="700" Background="{StaticResource FSE_PrimaryBackgroundBrush}" d:DataContext="{d:DesignInstance Type=vm:MainViewVM,IsDesignTimeCreatable=False}" Foreground="{StaticResource FSE_PrimaryForegroundBrush}"> <UserControl.Resources> <RadialGradientBrush x:Key="FSE_LED_GrayBrush"> @@ -25,7 +26,118 @@ </RadialGradientBrush> </UserControl.Resources> - <Grid> + <Grid IsEnabled="{Binding IsFree}" Background="Transparent"> + <Grid.Style> + <Style TargetType="Grid"> + <Setter Property="Cursor" Value="Arrow"></Setter> + <Style.Triggers> + <DataTrigger Binding="{Binding IsFree}" Value="False"> + <Setter Property="Cursor" Value="Wait"></Setter> + </DataTrigger> + </Style.Triggers> + </Style> + </Grid.Style> + + <Grid Margin="10"> + <DockPanel> + <DockPanel DockPanel.Dock="Top"> + <Image VerticalAlignment="Top" Source="/Images/machine_icon_none.png" Stretch="None" /> + + <StackPanel Margin="10 0 0 0" VerticalAlignment="Top"> + <TextBlock FontSize="{StaticResource FSE_LargeFontSize}">Tango Stubs Service</TextBlock> + <DockPanel Margin="0 5 0 0"> + <Ellipse Width="12" Height="12" Stroke="#353535"> + <Ellipse.Style> + <Style TargetType="Ellipse"> + <Setter Property="Fill" Value="{StaticResource FSE_LED_RedBrush}"></Setter> + <Style.Triggers> + <DataTrigger Binding="{Binding Service.IsConnected}" Value="True"> + <Setter Property="Fill" Value="{StaticResource FSE_LED_GreenBrush}"></Setter> + </DataTrigger> + </Style.Triggers> + </Style> + </Ellipse.Style> + </Ellipse> + <TextBlock Margin="5 0 0 0" FontWeight="SemiBold"> + <TextBlock.Style> + <Style TargetType="TextBlock"> + <Setter Property="Text" Value="Disconnected"></Setter> + <Setter Property="Foreground" Value="{StaticResource FSE_RedBrush}"></Setter> + <Style.Triggers> + <DataTrigger Binding="{Binding Service.IsConnected}" Value="True"> + <Setter Property="Text" Value="Connected"></Setter> + <Setter Property="Foreground" Value="{StaticResource FSE_GreenBrush}"></Setter> + </DataTrigger> + </Style.Triggers> + </Style> + </TextBlock.Style> + </TextBlock> + </DockPanel> + </StackPanel> + </DockPanel> + + <Grid Margin="0 20 0 0"> + <DockPanel> + + <Grid DockPanel.Dock="Top"> + <Border Padding="0 20"> + <DockPanel> + <Button Command="{Binding ToggleConnectionCommand}" Width="150" DockPanel.Dock="Right" Padding="8"> + <Button.Style> + <Style TargetType="Button" BasedOn="{StaticResource FSE_RaisedButton_Dark_Hover}"> + <Setter Property="Content" Value="CONNECT"/> + <Style.Triggers> + <DataTrigger Binding="{Binding Service.IsConnected}" Value="True"> + <Setter Property="Content" Value="DISCONNECT"/> + </DataTrigger> + </Style.Triggers> + </Style> + </Button.Style> + </Button> + <ComboBox DockPanel.Dock="Left" Margin="0 0 20 0" ItemsSource="{Binding AvailablePorts}" SelectedItem="{Binding SelectedPort}" IsEnabled="{Binding Service.IsConnected,Converter={StaticResource BooleanInverseConverter}}"></ComboBox> + </DockPanel> + </Border> + </Grid> + + <StackPanel Orientation="Horizontal" DockPanel.Dock="Bottom" Margin="2 5 0 0"> + <CheckBox IsChecked="{Binding Service.EnableLogs}"> + <TextBlock Margin="0 -3 0 0"> + Enable Communication Logs + </TextBlock> + </CheckBox> + + <CheckBox Margin="10 0 0 0" IsChecked="{Binding Settings.AutoConnect}"> + <TextBlock Margin="0 -3 0 0"> + Auto Connect on Startup + </TextBlock> + </CheckBox> + </StackPanel> + + <DockPanel Margin="0 10 0 0" > + <Border DockPanel.Dock="Top" Padding="4" Background="{StaticResource FSE_PrimaryBackgroundLightBrush}" CornerRadius="5 5 0 0"> + <DockPanel> + <Button Style="{StaticResource FSE_RaisedButton_Dark_Hover}" DockPanel.Dock="Right" Command="{Binding ClearLogCommand}" ToolTip="Clear log" Padding="1"> + <material:PackIcon Kind="BinEmpty" /> + </Button> + <TextBlock FontWeight="SemiBold" VerticalAlignment="Center">LOG</TextBlock> + </DockPanel> + </Border> + <Border Background="{StaticResource FSE_PrimaryBackgroundDarkBrush}" CornerRadius="0 0 5 5" BorderThickness="1" BorderBrush="{StaticResource FSE_PrimaryBackgroundLightBrush}" Padding="3"> + <!--<TextBox x:Name="txtLogs" Foreground="{StaticResource FSE_GrayBrush}" Style="{x:Null}" BorderThickness="0" HorizontalContentAlignment="Left" VerticalContentAlignment="Top" AcceptsReturn="True" IsReadOnly="True" Background="Transparent" FontSize="{StaticResource FSE_SmallFontSize}" Padding="5" HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Auto"></TextBox>--> + <controls:ScrollableFlowDocumentScrollViewer x:Name="scrollViewerLogs" HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Auto" Padding="5"> + <FlowDocument x:Name="documentLogs" FontFamily="{Binding RelativeSource={RelativeSource AncestorType=UserControl},Path=FontFamily}" FontSize="{StaticResource FSE_SmallFontSize}" Foreground="{StaticResource FSE_GrayBrush}" PagePadding="0"> + <Paragraph x:Name="paragraphLog"> + + </Paragraph> + </FlowDocument> + </controls:ScrollableFlowDocumentScrollViewer> + </Border> + </DockPanel> + </DockPanel> + </Grid> + </DockPanel> + </Grid> + <tb:TaskbarIcon x:Name="taskIcon" x:FieldModifier="public" Visibility="{Binding IsTrayIconVisible,Converter={StaticResource BooleanToVisibilityConverter}}" ToolTipText="Tango Stubs Service" diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml.cs index 1c51be6d4..a0dab9f79 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service.UI/Views/MainView.xaml.cs @@ -21,10 +21,13 @@ namespace Tango.StubsUtils.Service.UI.Views /// </summary> public partial class MainView : UserControl { + public static MainView Instance { get; set; } + public MainView() { InitializeComponent(); DataContext = new MainViewVM(); + Instance = this; } } } diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsService.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsService.cs index 05b2d518c..58af2d8ff 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsService.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsService.cs @@ -26,12 +26,12 @@ namespace Tango.StubsUtils.Service { public class StubsService : ExtendedObject { + private static int transporterCount = 1; private const string PIPE_NAME = "Tango_Stubs_Server"; private NamedPipeServerStream _server; private StreamReader _reader; private StreamWriter _writer; private BinaryFormatter _formatter; - private StubsServiceSettings _settings; private bool _initialized; private List<Type> _stubsTypes; private Dictionary<String, StubReflection> _stubsLookup; @@ -73,8 +73,7 @@ namespace Tango.StubsUtils.Service public StubsService() { - _settings = SettingsManager.Default.GetOrCreate<StubsServiceSettings>(); - _settings.Save(); + } #endregion @@ -141,13 +140,14 @@ namespace Tango.StubsUtils.Service #region Connect/Disconnect - public async Task Connect() + public async Task Connect(String comPort) { if (!IsStarted) throw new InvalidOperationException("Cannot connect the transporter before the service has started."); if (!IsConnected) { - Transporter = new BasicTransporter(new UsbTransportAdapter(_settings.USBPort)); + Transporter = new BasicTransporter(new UsbTransportAdapter(comPort)); + Transporter.ComponentName = $"Transporter {transporterCount++}"; Transporter.UseKeepAlive = false; await Transporter.Connect(); IsConnected = true; @@ -159,6 +159,7 @@ namespace Tango.StubsUtils.Service if (IsConnected) { await Transporter.Disconnect(); + IsConnected = false; } } @@ -180,30 +181,27 @@ namespace Tango.StubsUtils.Service var package = new StubPackageRequestDTO(); package.Arguments = request.Split(' '); - if (EnableLogs) LogManager.Log($"Stub package constructed: '{package.ToJsonString()}'..."); - var response = ProcessStubPackage(package); - if (EnableLogs) LogManager.Log($"Stub package response: '{response.ToJsonString()}'..."); + //if (EnableLogs) LogManager.Log($"Stub package response:\n'{response.ToJsonString()}'..."); _writer.Write(response.ToString()); _writer.Flush(); } catch (Exception ex) { - if (EnableLogs) LogManager.Log(ex, "Error processing stub package."); + LogManager.Log(ex, "Error processing stub package."); try { var response = new StubPackageResponseDTO() { Status = StubPackageResponseStatus.Error, - Message = $"Error processing stub package\n{ex.FlattenMessage()}" + Message = $"Error: {ex.GetFirstIfAggregate().Message}" }; _writer.WriteLine(response.ToString()); _writer.Flush(); - _server.Disconnect(); } catch { } } @@ -224,92 +222,81 @@ namespace Tango.StubsUtils.Service if (Transporter == null || Transporter.State != TransportComponentState.Connected) { - response.Status = StubPackageResponseStatus.NoConnection; - response.Message = "Machine is disconnected."; - return response; + throw new InvalidOperationException("Machine is disconnected"); } - try - { - if (EnableLogs) LogManager.Log("Processing package..."); + if (EnableLogs) LogManager.Log("Processing package..."); - String stubName = package.Arguments[0]; - List<String> arguments = package.Arguments.Skip(1).ToList(); + String stubName = package.Arguments[0]; + List<String> arguments = package.Arguments.Skip(1).ToList(); - StubReflection stubReflection = GetStubReflection(stubName); + StubReflection stubReflection = GetStubReflection(stubName); - MessageContainer requestContainer = new MessageContainer(); - requestContainer.Token = Guid.NewGuid().ToString(); - requestContainer.Type = stubReflection.MessageType; + MessageContainer requestContainer = new MessageContainer(); + requestContainer.Token = Guid.NewGuid().ToString(); + requestContainer.Type = stubReflection.MessageType; - IMessage request = Activator.CreateInstance(stubReflection.Type) as IMessage; + IMessage request = Activator.CreateInstance(stubReflection.Type) as IMessage; - for (int i = 0; i < arguments.Count; i++) - { - String argument = arguments[i]; + for (int i = 0; i < arguments.Count; i++) + { + String argument = arguments[i]; - if (i >= stubReflection.Properties.Count) - { - throw new ArgumentOutOfRangeException($"Argument '{argument}' index is out of range for stub '{stubReflection.Type.Name}'."); - } + if (i >= stubReflection.Properties.Count) + { + throw new ArgumentException($"Argument '{argument}' index is out of range for stub '{stubReflection.Type.Name}'."); + } - PropertyInfo prop = stubReflection.Properties[i]; + PropertyInfo prop = stubReflection.Properties[i]; - if (prop.PropertyType == typeof(UInt32)) - { - prop.SetValue(request, UInt32.Parse(argument)); - } - else if (prop.PropertyType == typeof(bool)) - { - prop.SetValue(request, bool.Parse(argument)); - } - else if (typeof(IList).IsAssignableFrom(prop.PropertyType)) - { - IList arr = prop.GetValue(request) as IList; - foreach (var item in argument.Split(',')) - { - object converted = Convert.ChangeType(item, prop.PropertyType.GetGenericArguments()[0]); - arr.Add(converted); - } - } - else + if (prop.PropertyType == typeof(UInt32)) + { + prop.SetValue(request, UInt32.Parse(argument)); + } + else if (prop.PropertyType == typeof(bool)) + { + prop.SetValue(request, bool.Parse(argument)); + } + else if (typeof(IList).IsAssignableFrom(prop.PropertyType)) + { + IList arr = prop.GetValue(request) as IList; + foreach (var item in argument.Split(',')) { - object converted = Convert.ChangeType(argument, prop.PropertyType); - prop.SetValue(request, converted); + object converted = Convert.ChangeType(item, prop.PropertyType.GetGenericArguments()[0]); + arr.Add(converted); } } + else + { + object converted = Convert.ChangeType(argument, prop.PropertyType); + prop.SetValue(request, converted); + } + } - if (EnableLogs) LogManager.Log($"Request stub constructed:\n{request.ToJsonString()}"); - - requestContainer.Data = request.ToByteString(); - var responseContainer = Transporter.SendRequest(requestContainer, new TransportRequestConfig() { ThreadingMode = TransportThreadingMode.ThreadPool }).Result; + if (EnableLogs) LogManager.Log($"Request stub constructed:\n{request.ToJsonString()}"); - var stubResponseReflection = GetStubReflection(responseContainer.Type.ToOriginalName()); - IMessage stubResponse = stubResponseReflection.Parser.ParseFrom(responseContainer.Data); + requestContainer.Data = request.ToByteString(); + var responseContainer = Transporter.SendRequest(requestContainer, new TransportRequestConfig() { ThreadingMode = TransportThreadingMode.ThreadPool }).Result; - String responseMessage = String.Empty; + var stubResponseReflection = GetStubReflection(responseContainer.Type.ToOriginalName()); + IMessage stubResponse = stubResponseReflection.Parser.ParseFrom(responseContainer.Data); - foreach (var prop in stubResponseReflection.Properties) - { - responseMessage += $"{prop.Name}: {prop.GetValue(stubResponse).ToStringSafe()}\n"; - } - - if (EnableLogs) - { - String responseJson = stubResponse.ToJsonString(); - LogManager.Log($"Response:\n{stubResponse}"); - } + String responseMessage = String.Empty; - response.Status = StubPackageResponseStatus.OK; - response.Message = responseMessage; + foreach (var prop in stubResponseReflection.Properties) + { + responseMessage += $"{prop.Name}: {prop.GetValue(stubResponse).ToStringSafe()}\n"; } - catch (Exception ex) + + if (EnableLogs) { - LogManager.Log(ex, "Error processing stub package."); - response.Status = StubPackageResponseStatus.Error; - response.Message = ex.FlattenMessage(); + String responseJson = stubResponse.ToJsonString(); + LogManager.Log($"Stub package response:\n{responseJson}"); } + response.Status = StubPackageResponseStatus.OK; + response.Message = responseMessage; + return response; } diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsServiceSettings.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsServiceSettings.cs index 8741065cf..e71fd2138 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsServiceSettings.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Service/StubsServiceSettings.cs @@ -9,11 +9,6 @@ namespace Tango.StubsUtils.Service { public class StubsServiceSettings : SettingsBase { - public String USBPort { get; set; } - public StubsServiceSettings() - { - USBPort = "COM1"; - } } } diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.SessionClient.CLI/Program.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.SessionClient.CLI/Program.cs index b72e15236..d384ebba6 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.SessionClient.CLI/Program.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.SessionClient.CLI/Program.cs @@ -37,7 +37,7 @@ namespace Tango.StubsUtils.SessionClient.CLI try { var _client = new NamedPipeClientStream(PIPE_NAME); - _client.Connect(5000); + _client.Connect(1000); var writer = new StreamWriter(_client); @@ -54,7 +54,8 @@ namespace Tango.StubsUtils.SessionClient.CLI } catch (Exception ex) { - OnError($"Error communicating with the stubs service. {ex.Message}"); + OnError($"Status: Error\nError: Error communicating with the stubs service. {ex.Message}"); + continue; } if (response.Status == StubPackageResponseStatus.OK) diff --git a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Shared/StubPackageResponseStatus.cs b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Shared/StubPackageResponseStatus.cs index 4edd47d6c..6577e629d 100644 --- a/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Shared/StubPackageResponseStatus.cs +++ b/Software/Visual_Studio/StubsUtils/Tango.StubsUtils.Shared/StubPackageResponseStatus.cs @@ -11,6 +11,5 @@ namespace Tango.StubsUtils.Shared { OK, Error, - NoConnection } } |
