From a652c9a10009fb15490921264c273323d8aaca82 Mon Sep 17 00:00:00 2001 From: Jerker Dahlblom Date: Sun, 26 Nov 2023 16:03:34 +0200 Subject: [PATCH] Losetcommand (#49) * Made server log API list in markdown list format. * LoSetCommand file now external, iCommands searchable * All iCommands contained in file iCommands.txt which user can export, info in wiki * iCommands can be searched * Compile --- src/client/DCSInsight/DCSInsight.csproj | 9 +- .../DCSInsight/Images/cue_banner_search.png | Bin 0 -> 2508 bytes src/client/DCSInsight/MainWindow.xaml | 3 + src/client/DCSInsight/MainWindow.xaml.cs | 19 +++ src/client/DCSInsight/Misc/LoSetCommand.cs | 26 ++-- .../DCSInsight/Misc/TextBoxSearchCommon.cs | 84 ++++++++++++ .../UserControls/UserControlAPIBase.cs | 1 - .../UserControlLoSetCommandAPI.xaml | 16 +++ .../UserControlLoSetCommandAPI.xaml.cs | 128 +++++++++++++++--- .../DCSInsight/{Items => }/iCommands.txt | 0 .../Scripts/DCS-INSIGHT/ServerSettings.lua | 2 +- .../Scripts/DCS-INSIGHT/lib/APIHandler.lua | 7 +- 12 files changed, 257 insertions(+), 38 deletions(-) create mode 100644 src/client/DCSInsight/Images/cue_banner_search.png create mode 100644 src/client/DCSInsight/Misc/TextBoxSearchCommon.cs rename src/client/DCSInsight/{Items => }/iCommands.txt (100%) diff --git a/src/client/DCSInsight/DCSInsight.csproj b/src/client/DCSInsight/DCSInsight.csproj index 47724a5..2edde4c 100644 --- a/src/client/DCSInsight/DCSInsight.csproj +++ b/src/client/DCSInsight/DCSInsight.csproj @@ -6,17 +6,17 @@ true dcs-insight 1.0.0 - 1.7.9 + 1.8.0 Images\Magnifier_icon.ico + - @@ -28,14 +28,15 @@ + - + Always - + diff --git a/src/client/DCSInsight/Images/cue_banner_search.png b/src/client/DCSInsight/Images/cue_banner_search.png new file mode 100644 index 0000000000000000000000000000000000000000..e82f998c9cc72e10ff676408cfb5ee7dbfab3050 GIT binary patch literal 2508 zcmV;-2{ZPIP)U8P*7-ZbZ>KLZ*U+lnSp_Ufq@}0xwybFAi#%#fq@|}KQEO56)-X|e7nZL z$iTqBa9P*U#mSX{G{Bl%P*lRez;J+pfx##xwK$o9f#C}S14DXwNkIt%17i#W1A|CX zc0maP17iUL1A|C*NRTrF17iyV0~1e4YDEbH0|SF|enDkXW_m`6f}y3QrGjHhep0GJ zaAk2xYHqQDXI^rCQ9*uDVo7QW0|Nup4h9AW240u^5(W3f%sd4n162kpgNVo|1qcff zJ_s=cNG>fZg9jx8g8+j9g8_pBLjXe}Lp{R+hNBE`7{wV~7)u#fFy3PlV+vxLz;uCG zm^qSpA@ds+OO_6nTdaDlt*rOhEZL^9ePa)2-_4=K(Z%tFGm-NGmm}8}ZcXk5JW@PU zd4+f<@d@)yL(o<5icqT158+-B6_LH7;i6x}CW#w~Uy-Pgl#@Irl`kzV zeL|*8R$ca%T%Wv){2zs_iiJvgN^h0dsuZZ2sQy$tsNSU!s;Q*;LF<6_B%M@UD?LHI zSNcZ`78uqV#TeU~$eS{ozBIdFzSClfs*^S+dw;4dus<{M;#|MXC)T}S9v!D zcV!QCPhBq)ZyO(X-(bH4|NMaZz==UigLj2o41F2S6d@OB6%`R(5i>J(Puzn9wnW{e zu;hl6HK{k#IWjCVGqdJqU(99Cv(K+6*i`tgSi2;vbXD1#3jNBGs$DgVwO(~o>mN4i zHPtkqZIx>)Y(Ls5-Br|mx>vQYvH$Kwn@O`L|D75??eGkZnfg$5<;Xeg_o%+-I&+-3%01W^SH2RkDT>t<8AY({UO#lFTB>(_`g8%^e z{{R4h=>PzAFaQARU;qF*m;eA5Z<1fdMgRZ?E=fc|RCwC#Sv_du*cSd~2?`@{2w2m| zU~ovGY3wbW;KDJCox)_yGB!LmouxWM*GldGXg^R2T7aPN7n|ZM8gA}_imrej{{v>n%JQ!oXc)@jmDLYg~% zmNJFAf}I`LX`}7DnF0xnH#yu4A4dCT*d+Ar0Hf0y4Xoq|ZzA2DWwdpg@V+bjnu2-o zY0&faO&d(%QUFHn4->K3{ca5dhLWYt{N{9RLE!opqO|+-seX8Gqk1+LfYbbsV=vhl43p{0_(M{XiA4 z>Nz3+rViHK&VyzE&^2_f6$(?#MW{ao00PyaO z#(P#1lQhp!J`1SzHJ+n(>YD|iu{67L(>&7w(tNZGC?z@OSxrn{hMA5WQ&VKbcsntf zb%zV?b@a-8r@O#TJu&eWnF#lqqkw2E&2z8kBB=wwsC~wa+S;)#29ln2^8oOyCibuo z$UR%+sAw5rG489P&f5%l^I*f^faW*_Tnfw&Z26XJMPRuZ3Wl!er@4RuaHu8Kx=yp! z%O3&b>*a`#(RjcV)D>X&2dar23+x+hjrSE3L+l3tMk*-ZZd@l^)>`%>%vvOyfZzHl zPz4hBxpQ6$kbQ34C&9alFmtxE$cguP`V)iLln3R9R#Jr2^_yX0s3y z(FB0CU$94_GN9PXkvldN)F2f!f3(a*0#)W8M)+UHo4rtQmS5;Zj#Y}>o2{Rm6GHGL zq83JN7HaBr*Sx@0b!Q%+7)VmDoKYGLX#7=hD%`KN#slPJG7)s_IEGi6=l;mvt#V_j zv84S@zqxUUlS5#*Y5sb#_|1YFkeCQn{aiTBs;Kz4Q-SKsAC=N6S|=Jkn?s`IHTpEG zgtafyccgne`0g0k4En6otP#GJx9*NWA&~s^+Qm*9zGKg?k_9ydtT=7&v&39(g_anF z9~|!rAEw;>zunY*7H}!Bmh(_ez?0uu=O|kod`65*52=h=zgeTOR(i;E%!@&4w)Ii~ ze3sm^#jWy&!CK4Li#I#YX8}grm3iNiF&*=QRACzZ$NBLl&00I_Ove`G?p5ZAeEGAzt*lbI6x@?GYLl6YO=XBvSMtCaGin1m z&03ySTdehswkfo-I?Y;C#=JOVOu=ZkvO0bLt%9UyotC>q)4M@60l7Epk~2o`jkg{B zmC4_d5waFoIOOBOZvy}s WXZZ88`Cpm<0000 dcs-insight + + wiki + diff --git a/src/client/DCSInsight/MainWindow.xaml.cs b/src/client/DCSInsight/MainWindow.xaml.cs index 4f0cdfc..c0bf74b 100644 --- a/src/client/DCSInsight/MainWindow.xaml.cs +++ b/src/client/DCSInsight/MainWindow.xaml.cs @@ -511,5 +511,24 @@ private void ButtonRangeTest_OnClick(object sender, RoutedEventArgs e) Common.ShowErrorMessageBox(ex); } } + + private void TextBlockAppWiki_OnMouseDown(object sender, MouseButtonEventArgs e) + { + Process.Start(new ProcessStartInfo + { + FileName = "https://github.com/DCS-Skunkworks/dcs-insight/wiki", + UseShellExecute = true + }); + } + + private void UIElement_OnMouseEnter(object sender, MouseEventArgs e) + { + Mouse.OverrideCursor = Cursors.Hand; + } + + private void UIElement_OnMouseLeave(object sender, MouseEventArgs e) + { + Mouse.OverrideCursor = Cursors.Arrow; + } } } diff --git a/src/client/DCSInsight/Misc/LoSetCommand.cs b/src/client/DCSInsight/Misc/LoSetCommand.cs index bc6651a..24d3361 100644 --- a/src/client/DCSInsight/Misc/LoSetCommand.cs +++ b/src/client/DCSInsight/Misc/LoSetCommand.cs @@ -1,31 +1,39 @@ -using System; +using NLog; +using System; using System.Collections.Generic; using System.IO; using System.Linq; using System.Windows; +using System.Windows.Shapes; namespace DCSInsight.Misc { internal class LoSetCommand { + private static readonly Logger Logger = LogManager.GetCurrentClassLogger(); + private const string CommandsFile = "iCommands.txt"; + public string Description { get; private set; } public string Code { get; private set; } internal static List LoadCommands() { var result = new List(); - var resourceStream = Application.GetResourceStream(new Uri(@"/dcs-insight;component/Items/iCommands.txt", UriKind.Relative)); - if (resourceStream == null) return result; + var loSetCommandsFile = $"{AppDomain.CurrentDomain.BaseDirectory}{CommandsFile}"; + if (!File.Exists(loSetCommandsFile)) + { + Logger.Error($"Failed to find {CommandsFile} in base directory."); + return result; + } - var streamReader = new StreamReader(resourceStream.Stream); - string line; + var stringArray = File.ReadAllLines(loSetCommandsFile); - while ((line = streamReader.ReadLine()) != null) + foreach (var s in stringArray) { - if(!line.Trim().StartsWith("i") || !line.Contains('\t') || line.Contains('/')) continue; + if (string.IsNullOrEmpty(s) || !s.Trim().StartsWith("i") || !s.Contains('\t') || s.Contains('/') || s.Contains(':')) continue; - var array = line.Split('\t'); - result.Add(new LoSetCommand{Code = array[1].Trim(), Description = array[0].Trim() }); + var array = s.Split('\t'); + result.Add(new LoSetCommand { Code = array[1].Trim(), Description = array[0].Trim() }); } result = result.OrderBy(o => o.Description).ToList(); diff --git a/src/client/DCSInsight/Misc/TextBoxSearchCommon.cs b/src/client/DCSInsight/Misc/TextBoxSearchCommon.cs new file mode 100644 index 0000000..aafddb9 --- /dev/null +++ b/src/client/DCSInsight/Misc/TextBoxSearchCommon.cs @@ -0,0 +1,84 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Windows.Controls; +using System.Windows.Controls.Primitives; +using System.Windows.Input; +using System.Windows.Media; +using System.Windows.Media.Imaging; + +namespace DCSInsight.Misc +{ + internal static class TextBoxSearchCommon + { + internal static void SetBackgroundSearchBanner(TextBox textBoxSearch) + { + try + { + //new Uri(@"/dcs-insight;component/Images/cue_banner_search.png", UriKind.Relative)), + if (string.IsNullOrEmpty(textBoxSearch.Text)) + { + // Create an ImageBrush. + var textImageBrush = new ImageBrush + { + ImageSource = new BitmapImage( + new Uri("pack://application:,,,/dcs-insight;component/Images/cue_banner_search.png", UriKind.RelativeOrAbsolute)), + AlignmentX = AlignmentX.Left, + Stretch = Stretch.Uniform + }; + + // Use the brush to paint the button's background. + textBoxSearch.Background = textImageBrush; + } + else + { + textBoxSearch.Background = null; + } + } + catch (Exception ex) + { + Common.ShowErrorMessageBox(ex); + } + } + + internal static void AdjustShownPopupData(TextBox textBoxSearch, Popup popupSearch, DataGrid dataGridValues, IEnumerable loSetCommands) + { + try + { + popupSearch.PlacementTarget = textBoxSearch; + popupSearch.Placement = PlacementMode.Bottom; + dataGridValues.Tag = textBoxSearch; + if (!popupSearch.IsOpen) + { + popupSearch.IsOpen = true; + } + + if (string.IsNullOrEmpty(textBoxSearch.Text)) + { + dataGridValues.DataContext = loSetCommands; + dataGridValues.ItemsSource = loSetCommands; + dataGridValues.Items.Refresh(); + return; + } + var subList = loSetCommands.Where(loSetCommand => (!string.IsNullOrWhiteSpace(loSetCommand.Description) && + loSetCommand.Description.ToUpper().Contains(textBoxSearch.Text.ToUpper())) + || (!string.IsNullOrWhiteSpace(loSetCommand.Code) && loSetCommand.Code.ToUpper().Contains(textBoxSearch.Text.ToUpper()))); + dataGridValues.DataContext = subList; + dataGridValues.ItemsSource = subList; + dataGridValues.Items.Refresh(); + } + catch (Exception ex) + { + Common.ShowErrorMessageBox(ex, "AdjustShownPopupData()"); + } + } + + internal static void HandleFirstSpace(object sender, KeyEventArgs e) + { + if (e.Key == Key.Space && ((TextBox)sender).Text == "") + { + e.Handled = true; + } + } + } +} diff --git a/src/client/DCSInsight/UserControls/UserControlAPIBase.cs b/src/client/DCSInsight/UserControls/UserControlAPIBase.cs index 65fe6e3..5ea3cb3 100644 --- a/src/client/DCSInsight/UserControls/UserControlAPIBase.cs +++ b/src/client/DCSInsight/UserControls/UserControlAPIBase.cs @@ -22,7 +22,6 @@ public abstract partial class UserControlAPIBase : UserControl, IDisposable, IAs protected readonly DCSAPI DCSAPI; protected bool IsControlLoaded; protected readonly List TextBoxParameterList = new(); - protected readonly List ComboBoxParameterList = new(); protected bool IsConnected; protected readonly Timer PollingTimer; protected bool CanSend; diff --git a/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml b/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml index 2db21f4..372e001 100644 --- a/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml +++ b/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml @@ -7,6 +7,22 @@ Loaded="UserControlLoSetCommandAPI_OnLoaded" mc:Ignorable="d" d:DesignHeight="400" d:DesignWidth="800" Height="auto" IsTabStop="True"> + + + + + + + + + + + + diff --git a/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml.cs b/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml.cs index ea12884..574f1a1 100644 --- a/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml.cs +++ b/src/client/DCSInsight/UserControls/UserControlLoSetCommandAPI.xaml.cs @@ -1,9 +1,11 @@ using System; using System.Collections.Generic; using System.Linq; +using System.Reflection; using System.Threading.Tasks; using System.Windows; using System.Windows.Controls; +using System.Windows.Controls.Primitives; using System.Windows.Input; using DCSInsight.Events; using DCSInsight.JSON; @@ -17,6 +19,12 @@ namespace DCSInsight.UserControls public partial class UserControlLoSetCommandAPI : UserControlAPIBase { + private Popup _popupSearch; + private DataGrid _dataGridValues; + private List _loSetCommands; + private LoSetCommand _loSetCommand; + private TextBox _textBoxSearch; + public UserControlLoSetCommandAPI(DCSAPI dcsAPI, bool isConnected) : base(dcsAPI, isConnected) { InitializeComponent(); @@ -40,6 +48,10 @@ private void UserControlLoSetCommandAPI_OnLoaded(object sender, RoutedEventArgs { if (IsControlLoaded) return; + _loSetCommands = LoSetCommand.LoadCommands(); + _popupSearch = (Popup)FindResource("PopUpSearchResults"); + _popupSearch.Height = 400; + _dataGridValues = (DataGrid)LogicalTreeHelper.FindLogicalNode(_popupSearch, "DataGridValues"); IsTabStop = true; BuildUI(); @@ -92,22 +104,24 @@ protected override void BuildUI() }; controlList.Add(label); - if (dcsAPIParameterType.ParameterName == "iCommand") + if (dcsAPIParameterType.ParameterName.StartsWith('i')) { var commands = LoSetCommand.LoadCommands(); - var comboBox = new ComboBox + _textBoxSearch = new TextBox { - Name = "ComboBox" + dcsAPIParameterType.Id, + Name = "TextBox" + dcsAPIParameterType.Id, Tag = dcsAPIParameterType.Id, - MinWidth = 100, + MinWidth = 150, MaxWidth = 350, Height = 20, - IsReadOnly = true, - DisplayMemberPath = "Description", - ItemsSource = commands }; - controlList.Add(comboBox); - ComboBoxParameterList.Add(comboBox); + + _textBoxSearch.TextChanged += TextBoxSearch_OnTextChanged; + _textBoxSearch.KeyUp += TextBoxSearch_OnKeyUp; + _textBoxSearch.PreviewKeyDown += TextBoxSearch_PreviewKeyDown; + TextBoxSearchCommon.SetBackgroundSearchBanner(_textBoxSearch); + controlList.Add(_textBoxSearch); + TextBoxParameterList.Add(_textBoxSearch); } else { @@ -218,7 +232,12 @@ protected override void BuildUI() Mouse.OverrideCursor = Cursors.Arrow; } } - + + private void TextBox_PreviewKeyDown(object sender, KeyEventArgs e) + { + throw new NotImplementedException(); + } + public override void SetResult(DCSAPI dcsApi) { try @@ -245,18 +264,6 @@ protected override void SendCommand() { try { - foreach (var comboBox in ComboBoxParameterList) - { - var parameterId = (int)comboBox.Tag; - foreach (var parameter in DCSAPI.Parameters) - { - if (parameter.Id == parameterId) - { - var loSetCommand = (LoSetCommand)comboBox.SelectedItem; - parameter.Value = loSetCommand.Code; - } - } - } foreach (var textBox in TextBoxParameterList) { var parameterId = (int)textBox.Tag; @@ -277,5 +284,82 @@ protected override void SendCommand() Common.ShowErrorMessageBox(ex); } } + + private void Selector_OnSelectionChanged(object sender, SelectionChangedEventArgs e) + { + try + { + if (_dataGridValues.SelectedItems.Count == 1) + { + _loSetCommand = (LoSetCommand)_dataGridValues.SelectedItem; + _textBoxSearch.Text = _loSetCommand.Code; + } + SetFormState(); + } + catch (Exception ex) + { + Common.ShowErrorMessageBox(ex); + } + } + + private void Control_OnMouseDoubleClick(object sender, MouseButtonEventArgs e) + { + try + { + if (_dataGridValues.SelectedItems.Count == 1) + { + _loSetCommand = (LoSetCommand)_dataGridValues.SelectedItem; + _textBoxSearch.Text = _loSetCommand.Code; + SetFormState(); + } + _popupSearch.IsOpen = false; + SetFormState(); + } + catch (Exception ex) + { + Common.ShowErrorMessageBox(ex); + } + } + + private void UIElement_OnMouseDown(object sender, MouseButtonEventArgs e) + { + try + { + if (_dataGridValues.SelectedItems.Count == 1) + { + _loSetCommand = (LoSetCommand)_dataGridValues.SelectedItem; + _textBoxSearch.Text = _loSetCommand.Code; + } + _popupSearch.IsOpen = false; + SetFormState(); + } + catch (Exception ex) + { + Common.ShowErrorMessageBox(ex); + } + } + + private void TextBoxSearch_OnKeyUp(object sender, KeyEventArgs e) + { + try + { + TextBoxSearchCommon.AdjustShownPopupData(((TextBox)sender), _popupSearch, _dataGridValues, _loSetCommands); + SetFormState(); + } + catch (Exception ex) + { + Common.ShowErrorMessageBox(ex); + } + } + + private void TextBoxSearch_OnTextChanged(object sender, TextChangedEventArgs e) + { + TextBoxSearchCommon.SetBackgroundSearchBanner(((TextBox)sender)); + } + + private void TextBoxSearch_PreviewKeyDown(object sender, KeyEventArgs e) + { + TextBoxSearchCommon.HandleFirstSpace(sender, e); + } } } diff --git a/src/client/DCSInsight/Items/iCommands.txt b/src/client/DCSInsight/iCommands.txt similarity index 100% rename from src/client/DCSInsight/Items/iCommands.txt rename to src/client/DCSInsight/iCommands.txt diff --git a/src/server/Scripts/DCS-INSIGHT/ServerSettings.lua b/src/server/Scripts/DCS-INSIGHT/ServerSettings.lua index 503ee3c..040e831 100644 --- a/src/server/Scripts/DCS-INSIGHT/ServerSettings.lua +++ b/src/server/Scripts/DCS-INSIGHT/ServerSettings.lua @@ -9,6 +9,6 @@ ServerSettings.TCP_address = "*" ServerSettings.TCP_port = 7790 -- Log incoming and outgoing JSON -ServerSettings.Log_JSON = false +ServerSettings.Log_JSON = true return ServerSettings diff --git a/src/server/Scripts/DCS-INSIGHT/lib/APIHandler.lua b/src/server/Scripts/DCS-INSIGHT/lib/APIHandler.lua index 3e6acfc..dd6a7fd 100644 --- a/src/server/Scripts/DCS-INSIGHT/lib/APIHandler.lua +++ b/src/server/Scripts/DCS-INSIGHT/lib/APIHandler.lua @@ -320,7 +320,12 @@ end function APIHandler:verify_entries() local message = "Following api have been loaded :\n" for i = 1, #self.commandsTable do - message = message .. self.commandsTable[i].id .. " : " .. self.commandsTable[i].apiInfo.api_syntax .. "\n" + message = message + .. "* " + .. self.commandsTable[i].id + .. " : " + .. self.commandsTable[i].apiInfo.api_syntax + .. "\n" end Log:log(message)