|
@@ -2,42 +2,221 @@
|
|
|
using System.Collections.Generic;
|
|
|
using System.Linq;
|
|
|
using System.Text;
|
|
|
-using ColorHelper;
|
|
|
using Terminal.Gui;
|
|
|
+using static System.Runtime.InteropServices.JavaScript.JSType;
|
|
|
|
|
|
namespace UICatalog.Scenarios;
|
|
|
|
|
|
-
|
|
|
-
|
|
|
-[ScenarioMetadata ("Ansi Requests", "Demonstration of how to send ansi requests.")]
|
|
|
-[ScenarioCategory ("Colors")]
|
|
|
-[ScenarioCategory ("Drawing")]
|
|
|
-public class AnsiRequestsScenario : Scenario
|
|
|
+[ScenarioMetadata ("AnsiEscapeSequenceRequest", "Ansi Escape Sequence Request")]
|
|
|
+[ScenarioCategory ("Ansi Escape Sequence")]
|
|
|
+public sealed class AnsiEscapeSequenceRequests : Scenario
|
|
|
{
|
|
|
private GraphView _graphView;
|
|
|
- private Window _win;
|
|
|
|
|
|
private DateTime start = DateTime.Now;
|
|
|
private ScatterSeries _sentSeries;
|
|
|
private ScatterSeries _answeredSeries;
|
|
|
|
|
|
- private List<DateTime> sends = new ();
|
|
|
+ private List<DateTime> sends = new ();
|
|
|
|
|
|
private object lockAnswers = new object ();
|
|
|
- private Dictionary<DateTime,string> answers = new ();
|
|
|
+ private Dictionary<DateTime, string> answers = new ();
|
|
|
private Label _lblSummary;
|
|
|
|
|
|
public override void Main ()
|
|
|
{
|
|
|
+ // Init
|
|
|
Application.Init ();
|
|
|
|
|
|
- _win = new Window { Title = $"{Application.QuitKey} to Quit - Scenario: {GetName ()}" };
|
|
|
+ TabView tv = new TabView
|
|
|
+ {
|
|
|
+ Width = Dim.Fill (),
|
|
|
+ Height = Dim.Fill ()
|
|
|
+ };
|
|
|
+
|
|
|
+ Tab single = new Tab ();
|
|
|
+ single.DisplayText = "Single";
|
|
|
+ single.View = BuildSingleTab ();
|
|
|
+
|
|
|
+ Tab bulk = new ();
|
|
|
+ bulk.DisplayText = "Multi";
|
|
|
+ bulk.View = BuildBulkTab ();
|
|
|
+
|
|
|
+ tv.AddTab (single, true);
|
|
|
+ tv.AddTab (bulk, false);
|
|
|
+
|
|
|
+ // Setup - Create a top-level application window and configure it.
|
|
|
+ Window appWindow = new ()
|
|
|
+ {
|
|
|
+ Title = GetQuitKeyAndName (),
|
|
|
+ };
|
|
|
+
|
|
|
+ appWindow.Add (tv);
|
|
|
+
|
|
|
+ // Run - Start the application.
|
|
|
+ Application.Run (appWindow);
|
|
|
+ bulk.View.Dispose ();
|
|
|
+ single.View.Dispose ();
|
|
|
+ appWindow.Dispose ();
|
|
|
+
|
|
|
+ // Shutdown - Calling Application.Shutdown is required.
|
|
|
+ Application.Shutdown ();
|
|
|
+ }
|
|
|
+
|
|
|
+ private View BuildSingleTab ()
|
|
|
+ {
|
|
|
+ View w = new View ()
|
|
|
+ {
|
|
|
+ Width = Dim.Fill (),
|
|
|
+ Height = Dim.Fill ()
|
|
|
+ };
|
|
|
+
|
|
|
+ w.Padding.Thickness = new (1);
|
|
|
+
|
|
|
+ var scrRequests = new List<string>
|
|
|
+ {
|
|
|
+ "CSI_SendDeviceAttributes",
|
|
|
+ "CSI_ReportTerminalSizeInChars",
|
|
|
+ "CSI_RequestCursorPositionReport",
|
|
|
+ "CSI_SendDeviceAttributes2"
|
|
|
+ };
|
|
|
+
|
|
|
+ var cbRequests = new ComboBox () { Width = 40, Height = 5, ReadOnly = true, Source = new ListWrapper<string> (new (scrRequests)) };
|
|
|
+ w.Add (cbRequests);
|
|
|
+
|
|
|
+ var label = new Label { Y = Pos.Bottom (cbRequests) + 1, Text = "Request:" };
|
|
|
+ var tfRequest = new TextField { X = Pos.Left (label), Y = Pos.Bottom (label), Width = 20 };
|
|
|
+ w.Add (label, tfRequest);
|
|
|
+
|
|
|
+ label = new Label { X = Pos.Right (tfRequest) + 1, Y = Pos.Top (tfRequest) - 1, Text = "Value:" };
|
|
|
+ var tfValue = new TextField { X = Pos.Left (label), Y = Pos.Bottom (label), Width = 6 };
|
|
|
+ w.Add (label, tfValue);
|
|
|
+
|
|
|
+ label = new Label { X = Pos.Right (tfValue) + 1, Y = Pos.Top (tfValue) - 1, Text = "Terminator:" };
|
|
|
+ var tfTerminator = new TextField { X = Pos.Left (label), Y = Pos.Bottom (label), Width = 4 };
|
|
|
+ w.Add (label, tfTerminator);
|
|
|
+
|
|
|
+ cbRequests.SelectedItemChanged += (s, e) =>
|
|
|
+ {
|
|
|
+ if (cbRequests.SelectedItem == -1)
|
|
|
+ {
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ var selAnsiEscapeSequenceRequestName = scrRequests [cbRequests.SelectedItem];
|
|
|
+ AnsiEscapeSequenceRequest selAnsiEscapeSequenceRequest = null;
|
|
|
+
|
|
|
+ switch (selAnsiEscapeSequenceRequestName)
|
|
|
+ {
|
|
|
+ case "CSI_SendDeviceAttributes":
|
|
|
+ selAnsiEscapeSequenceRequest = EscSeqUtils.CSI_SendDeviceAttributes;
|
|
|
+
|
|
|
+ break;
|
|
|
+ case "CSI_ReportTerminalSizeInChars":
|
|
|
+ selAnsiEscapeSequenceRequest = EscSeqUtils.CSI_ReportTerminalSizeInChars;
|
|
|
+
|
|
|
+ break;
|
|
|
+ case "CSI_RequestCursorPositionReport":
|
|
|
+ selAnsiEscapeSequenceRequest = EscSeqUtils.CSI_RequestCursorPositionReport;
|
|
|
+
|
|
|
+ break;
|
|
|
+ case "CSI_SendDeviceAttributes2":
|
|
|
+ selAnsiEscapeSequenceRequest = EscSeqUtils.CSI_SendDeviceAttributes2;
|
|
|
+
|
|
|
+ break;
|
|
|
+ }
|
|
|
+
|
|
|
+ tfRequest.Text = selAnsiEscapeSequenceRequest is { } ? selAnsiEscapeSequenceRequest.Request : "";
|
|
|
+ tfValue.Text = selAnsiEscapeSequenceRequest is { } ? selAnsiEscapeSequenceRequest.Value ?? "" : "";
|
|
|
+ tfTerminator.Text = selAnsiEscapeSequenceRequest is { } ? selAnsiEscapeSequenceRequest.Terminator : "";
|
|
|
+ };
|
|
|
+
|
|
|
+ // Forces raise cbRequests.SelectedItemChanged to update TextFields
|
|
|
+ cbRequests.SelectedItem = 0;
|
|
|
+
|
|
|
+ label = new Label { Y = Pos.Bottom (tfRequest) + 2, Text = "Response:" };
|
|
|
+ var tvResponse = new TextView { X = Pos.Left (label), Y = Pos.Bottom (label), Width = 40, Height = 4, ReadOnly = true };
|
|
|
+ w.Add (label, tvResponse);
|
|
|
+
|
|
|
+ label = new Label { X = Pos.Right (tvResponse) + 1, Y = Pos.Top (tvResponse) - 1, Text = "Error:" };
|
|
|
+ var tvError = new TextView { X = Pos.Left (label), Y = Pos.Bottom (label), Width = 40, Height = 4, ReadOnly = true };
|
|
|
+ w.Add (label, tvError);
|
|
|
+
|
|
|
+ label = new Label { X = Pos.Right (tvError) + 1, Y = Pos.Top (tvError) - 1, Text = "Value:" };
|
|
|
+ var tvValue = new TextView { X = Pos.Left (label), Y = Pos.Bottom (label), Width = 6, Height = 4, ReadOnly = true };
|
|
|
+ w.Add (label, tvValue);
|
|
|
+
|
|
|
+ label = new Label { X = Pos.Right (tvValue) + 1, Y = Pos.Top (tvValue) - 1, Text = "Terminator:" };
|
|
|
+ var tvTerminator = new TextView { X = Pos.Left (label), Y = Pos.Bottom (label), Width = 4, Height = 4, ReadOnly = true };
|
|
|
+ w.Add (label, tvTerminator);
|
|
|
+
|
|
|
+ var btnResponse = new Button { X = Pos.Center (), Y = Pos.Bottom (tvResponse) + 2, Text = "Send Request", IsDefault = true };
|
|
|
+
|
|
|
+ var lblSuccess = new Label { X = Pos.Center (), Y = Pos.Bottom (btnResponse) + 1 };
|
|
|
+ w.Add (lblSuccess);
|
|
|
+
|
|
|
+ Application.Driver.GetParser ().StoppedExpecting += (s,e)=>OnFail(e.CurrentValue,tvResponse,tvError,tvValue,tvTerminator, lblSuccess);
|
|
|
+
|
|
|
+ btnResponse.Accepting += (s, e) =>
|
|
|
+ {
|
|
|
+ var ansiEscapeSequenceRequest = new AnsiEscapeSequenceRequest
|
|
|
+ {
|
|
|
+ Request = tfRequest.Text,
|
|
|
+ Terminator = tfTerminator.Text,
|
|
|
+ Value = string.IsNullOrEmpty (tfValue.Text) ? null : tfValue.Text
|
|
|
+ };
|
|
|
+
|
|
|
+ Application.Driver.QueueAnsiRequest (
|
|
|
+ new ()
|
|
|
+ {
|
|
|
+ Request = ansiEscapeSequenceRequest.Request,
|
|
|
+ Terminator = ansiEscapeSequenceRequest.Terminator,
|
|
|
+ ResponseReceived = (s)=>OnSuccess(s, tvResponse, tvError, tvValue, tvTerminator,lblSuccess)
|
|
|
+ });
|
|
|
+ };
|
|
|
+
|
|
|
+ w.Add (btnResponse);
|
|
|
+
|
|
|
+ w.Add (new Label { Y = Pos.Bottom (lblSuccess) + 2, Text = "You can send other requests by editing the TextFields." });
|
|
|
+
|
|
|
+ return w;
|
|
|
+ }
|
|
|
+
|
|
|
+ private void OnSuccess (string response, TextView tvResponse, TextView tvError, TextView tvValue, TextView tvTerminator,Label lblSuccess)
|
|
|
+ {
|
|
|
+ tvResponse.Text = response;
|
|
|
+ tvError.Text = string.Empty;
|
|
|
+ tvValue.Text = string.Empty;
|
|
|
+ tvTerminator.Text = string.Empty;
|
|
|
+
|
|
|
+ lblSuccess.ColorScheme = Colors.ColorSchemes ["Base"];
|
|
|
+ lblSuccess.Text = "Successful";
|
|
|
+ }
|
|
|
+
|
|
|
+ private void OnFail (string terminator, TextView tvResponse, TextView tvError, TextView tvValue, TextView tvTerminator, Label lblSuccess)
|
|
|
+ {
|
|
|
+ tvResponse.Text = string.Empty;
|
|
|
+ tvError.Text = "No Response";
|
|
|
+ tvValue.Text = string.Empty;
|
|
|
+ tvTerminator.Text = terminator;
|
|
|
+
|
|
|
+ lblSuccess.ColorScheme = Colors.ColorSchemes ["Error"];
|
|
|
+ lblSuccess.Text = "Error";
|
|
|
+ }
|
|
|
+
|
|
|
+ private View BuildBulkTab ()
|
|
|
+ {
|
|
|
+ View w = new View ()
|
|
|
+ {
|
|
|
+ Width = Dim.Fill (),
|
|
|
+ Height = Dim.Fill ()
|
|
|
+ };
|
|
|
|
|
|
var lbl = new Label ()
|
|
|
{
|
|
|
Text = "This scenario tests Ansi request/response processing. Use the TextView to ensure regular user interaction continues as normal during sends",
|
|
|
Height = 2,
|
|
|
- Width = Dim.Fill()
|
|
|
+ Width = Dim.Fill ()
|
|
|
};
|
|
|
|
|
|
Application.AddTimeout (
|
|
@@ -60,7 +239,7 @@ public class AnsiRequestsScenario : Scenario
|
|
|
{
|
|
|
Y = Pos.Bottom (lbl),
|
|
|
Width = Dim.Percent (50),
|
|
|
- Height = Dim.Fill()
|
|
|
+ Height = Dim.Fill ()
|
|
|
};
|
|
|
|
|
|
|
|
@@ -78,13 +257,13 @@ public class AnsiRequestsScenario : Scenario
|
|
|
};
|
|
|
|
|
|
cbDar.ValueChanging += (s, e) =>
|
|
|
- {
|
|
|
- if (e.NewValue < 0 || e.NewValue > 20)
|
|
|
- {
|
|
|
- e.Cancel = true;
|
|
|
- }
|
|
|
- };
|
|
|
- _win.Add (cbDar);
|
|
|
+ {
|
|
|
+ if (e.NewValue < 0 || e.NewValue > 20)
|
|
|
+ {
|
|
|
+ e.Cancel = true;
|
|
|
+ }
|
|
|
+ };
|
|
|
+ w.Add (cbDar);
|
|
|
|
|
|
int lastSendTime = Environment.TickCount;
|
|
|
object lockObj = new object ();
|
|
@@ -116,35 +295,32 @@ public class AnsiRequestsScenario : Scenario
|
|
|
{
|
|
|
Y = Pos.Bottom (cbDar),
|
|
|
X = Pos.Right (tv),
|
|
|
- Width = Dim.Fill(),
|
|
|
- Height = Dim.Fill(1)
|
|
|
+ Width = Dim.Fill (),
|
|
|
+ Height = Dim.Fill (1)
|
|
|
};
|
|
|
|
|
|
_lblSummary = new Label ()
|
|
|
{
|
|
|
Y = Pos.Bottom (_graphView),
|
|
|
X = Pos.Right (tv),
|
|
|
- Width = Dim.Fill()
|
|
|
+ Width = Dim.Fill ()
|
|
|
};
|
|
|
|
|
|
SetupGraph ();
|
|
|
|
|
|
- _win.Add (lbl);
|
|
|
- _win.Add (lblDar);
|
|
|
- _win.Add (cbDar);
|
|
|
- _win.Add (tv);
|
|
|
- _win.Add (_graphView);
|
|
|
- _win.Add (_lblSummary);
|
|
|
+ w.Add (lbl);
|
|
|
+ w.Add (lblDar);
|
|
|
+ w.Add (cbDar);
|
|
|
+ w.Add (tv);
|
|
|
+ w.Add (_graphView);
|
|
|
+ w.Add (_lblSummary);
|
|
|
|
|
|
- Application.Run (_win);
|
|
|
- _win.Dispose ();
|
|
|
- Application.Shutdown ();
|
|
|
+ return w;
|
|
|
}
|
|
|
-
|
|
|
private void UpdateResponses ()
|
|
|
{
|
|
|
_lblSummary.Text = GetSummary ();
|
|
|
- _lblSummary.SetNeedsDisplay();
|
|
|
+ _lblSummary.SetNeedsDisplay ();
|
|
|
}
|
|
|
|
|
|
private string GetSummary ()
|
|
@@ -157,8 +333,8 @@ public class AnsiRequestsScenario : Scenario
|
|
|
var last = answers.Last ().Value;
|
|
|
|
|
|
var unique = answers.Values.Distinct ().Count ();
|
|
|
- var total = answers.Count;
|
|
|
-
|
|
|
+ var total = answers.Count;
|
|
|
+
|
|
|
return $"Last:{last} U:{unique} T:{total}";
|
|
|
}
|
|
|
|
|
@@ -193,7 +369,7 @@ public class AnsiRequestsScenario : Scenario
|
|
|
.Select (g => new PointF (g.Key, g.Count ()))
|
|
|
.ToList ();
|
|
|
// _graphView.ScrollOffset = new PointF(,0);
|
|
|
- _graphView.SetNeedsDisplay();
|
|
|
+ _graphView.SetNeedsDisplay ();
|
|
|
|
|
|
}
|
|
|
|
|
@@ -207,7 +383,7 @@ public class AnsiRequestsScenario : Scenario
|
|
|
Application.Driver.QueueAnsiRequest (
|
|
|
new ()
|
|
|
{
|
|
|
- Request = EscSeqUtils.CSI_SendDeviceAttributes,
|
|
|
+ Request = EscSeqUtils.CSI_SendDeviceAttributes.Request,
|
|
|
Terminator = EscSeqUtils.CSI_ReportDeviceAttributes_Terminator,
|
|
|
ResponseReceived = HandleResponse
|
|
|
});
|
|
@@ -218,7 +394,7 @@ public class AnsiRequestsScenario : Scenario
|
|
|
{
|
|
|
lock (lockAnswers)
|
|
|
{
|
|
|
- answers.Add (DateTime.Now,response);
|
|
|
+ answers.Add (DateTime.Now, response);
|
|
|
}
|
|
|
}
|
|
|
-}
|
|
|
+}
|