diff --git a/.vscode/tasks.json b/.vscode/tasks.json index 8af661d..0056896 100644 --- a/.vscode/tasks.json +++ b/.vscode/tasks.json @@ -16,7 +16,12 @@ "args": [ "-c", "Invoke-Build", - "Build" + // Build both modules + //"Build -ModuleName Microsoft.PowerShell.GraphicalTools, Microsoft.PowerShell.ConsoleGuiTools", + // Build only Out-GridView + //"Build -ModuleName Microsoft.PowerShell.GraphicalTools", + // Build only Out-ConsoleGridView + "Build -ModuleName Microsoft.PowerShell.ConsoleGuiTools", ], "problemMatcher": "$msCompile", "group": { diff --git a/Build.ps1 b/Build.ps1 index 7a885af..fd2eeff 100644 --- a/Build.ps1 +++ b/Build.ps1 @@ -1,3 +1,11 @@ -Invoke-Build Build -pwsh -noprofile -command "Import-Module -verbose '$PSScriptRoot/module/Microsoft.PowerShell.GraphicalTools'; Get-Process | Out-GridView -PassThru" -pwsh -noprofile -command "Import-Module -verbose '$PSScriptRoot/module/Microsoft.PowerShell.ConsoleGuiTools'; Get-Process | Out-ConsoleGridView -OutputMode Single" \ No newline at end of file +# Build script for buildling/testing from the commnad line. See tasks.json for how build is invoked within VS Code +# GraphicalTools includes two modules: Microsoft.PowerShell.GraphicalTools and Microsoft.PowerShell.ConsoleGuiTools +# To build them all leave -ModuleName off the `InvokeBuild` command (e.g. Invoke-Build Build). +# To build only one, specify it using the -ModuleName paramater (e.g. Invoke-Build Build -ModuleName Microsoft.PowerShell.ConsoleGuiTools). + +# Build... +Invoke-Build Build -ModuleName Microsoft.PowerShell.ConsoleGuiTools + +# Run what was built... +# pwsh -noprofile -command "Import-Module -verbose '$PSScriptRoot/module/Microsoft.PowerShell.GraphicalTools'; Get-Module -all | Out-GridView -OutputMode Single -Title 'Imported Modules' +pwsh -noprofile -command "Import-Module -verbose '$PSScriptRoot/module/Microsoft.PowerShell.ConsoleGuiTools'; Get-Module -all | Out-ConsoleGridView -OutputMode Single -Title 'Imported Modules' -Filter power" \ No newline at end of file diff --git a/GraphicalTools.build.ps1 b/GraphicalTools.build.ps1 index dd3d3c7..dbbeef9 100644 --- a/GraphicalTools.build.ps1 +++ b/GraphicalTools.build.ps1 @@ -3,7 +3,9 @@ param( [ValidateSet("Debug", "Release")] [string]$Configuration = "Debug", - [string[]]$ModuleName = @( "Microsoft.PowerShell.GraphicalTools", "Microsoft.PowerShell.ConsoleGuiTools" ) + [string[]]$ModuleName = @( + "Microsoft.PowerShell.GraphicalTools", + "Microsoft.PowerShell.ConsoleGuiTools" ) ) $script:IsUnix = $PSVersionTable.PSEdition -and $PSVersionTable.PSEdition -eq "Core" -and !$IsWindows diff --git a/src/Microsoft.PowerShell.ConsoleGuiTools/ConsoleGui.cs b/src/Microsoft.PowerShell.ConsoleGuiTools/ConsoleGui.cs index 78e76ad..00be36f 100644 --- a/src/Microsoft.PowerShell.ConsoleGuiTools/ConsoleGui.cs +++ b/src/Microsoft.PowerShell.ConsoleGuiTools/ConsoleGui.cs @@ -14,8 +14,13 @@ namespace OutGridView.Cmdlet internal class ConsoleGui : IDisposable { private const string FILTER_LABEL = "Filter"; + // This adjusts the left margin of all controls + private const int MARGIN_LEFT = 2; + // Width of Terminal.Gui ListView selection/check UI elements (old == 4, new == 2) + private const int CHECK_WIDTH = 4; private bool _cancelled; private GridViewDataSource _itemSource; + private Label _filterLabel; private TextField _filterField; private ListView _listView; private ApplicationData _applicationData; @@ -28,9 +33,8 @@ public HashSet Start(ApplicationData applicationData) _gridViewDetails = new GridViewDetails { // If OutputMode is Single or Multiple, then we make items selectable. If we make them selectable, - // they have a 8 character addition of a checkbox (".....[ ]" or ".....( )") - // that we have to factor in. - ListViewOffset = _applicationData.OutputMode != OutputModeOption.None ? 8 : 4 + // 2 columns are required for the check/selection indicator and space. + ListViewOffset = _applicationData.OutputMode != OutputModeOption.None ? MARGIN_LEFT + CHECK_WIDTH : MARGIN_LEFT }; Window win = AddTopLevelWindow(); @@ -91,7 +95,7 @@ private Window AddTopLevelWindow() Y = 0, // By using Dim.Fill(), it will automatically resize without manual intervention Width = Dim.Fill(), - Height = Dim.Fill() + Height = Dim.Fill(1) }; Application.Top.Add(win); @@ -166,8 +170,7 @@ private void CalculateColumnWidths(List gridHeaders) } // if the total width is wider than the usable width, remove 1 from widest column until it fits - // the gui loses 3 chars on the left and 2 chars on the right - _gridViewDetails.UsableWidth = Application.Top.Frame.Width - 3 - listViewColumnWidths.Length - _gridViewDetails.ListViewOffset - 2; + _gridViewDetails.UsableWidth = Application.Top.Frame.Width - MARGIN_LEFT - listViewColumnWidths.Length - _gridViewDetails.ListViewOffset; int columnWidthsSum = listViewColumnWidths.Sum(); while (columnWidthsSum >= _gridViewDetails.UsableWidth) { @@ -189,25 +192,25 @@ private void CalculateColumnWidths(List gridHeaders) private void AddFilter(Window win) { - var filterLabel = new Label(FILTER_LABEL) + _filterLabel = new Label(FILTER_LABEL) { - X = 2 + X = MARGIN_LEFT }; _filterField = new TextField(string.Empty) { - X = Pos.Right(filterLabel) + 1, - Y = Pos.Top(filterLabel), + X = Pos.Right(_filterLabel) + 1, + Y = Pos.Top(_filterLabel), CanFocus = true, - Width = Dim.Fill() - filterLabel.Text.Length + Width = Dim.Fill() - _filterLabel.Text.Length }; var filterErrorLabel = new Label(string.Empty) { - X = Pos.Right(filterLabel) + 1, - Y = Pos.Top(filterLabel) + 1, + X = Pos.Right(_filterLabel) + 1, + Y = Pos.Top(_filterLabel) + 1, ColorScheme = Colors.Base, - Width = Dim.Fill() - filterLabel.Text.Length + Width = Dim.Fill() - _filterLabel.Text.Length }; _filterField.TextChanged += (str) => @@ -232,14 +235,14 @@ private void AddFilter(Window win) } }; - win.Add(filterLabel, _filterField, filterErrorLabel); + win.Add(_filterLabel, _filterField, filterErrorLabel); } private void AddHeaders(Window win, List gridHeaders) { var header = new Label(GridViewHelpers.GetPaddedString( gridHeaders, - _gridViewDetails.ListViewOffset + _gridViewDetails.ListViewOffset - 1, + _gridViewDetails.ListViewOffset, _gridViewDetails.ListViewColumnWidths)) { X = 0, @@ -286,7 +289,7 @@ private void LoadData() valueList.Add(dataValue); } - string displayString = GridViewHelpers.GetPaddedString(valueList, _gridViewDetails.ListViewOffset, _gridViewDetails.ListViewColumnWidths); + string displayString = GridViewHelpers.GetPaddedString(valueList, 0, _gridViewDetails.ListViewColumnWidths); items.Add(new GridViewRow { @@ -304,10 +307,10 @@ private void AddRows(Window win) { _listView = new ListView(_itemSource) { - X = 3, - Y = 4, + X = Pos.Left(_filterLabel), + Y = Pos.Bottom(_filterLabel) + 3, // 1 for space, 1 for header, 1 for header underline Width = Dim.Fill(2), - Height = Dim.Fill(2), + Height = Dim.Fill(), AllowsMarking = _applicationData.OutputMode != OutputModeOption.None, AllowsMultipleSelection = _applicationData.OutputMode == OutputModeOption.Multiple, }; diff --git a/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDataSource.cs b/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDataSource.cs index ff82fb5..f8047ce 100644 --- a/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDataSource.cs +++ b/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDataSource.cs @@ -47,7 +47,7 @@ private void RenderUstr(ConsoleDriver driver, ustring ustr, int col, int line, i { (var rune, var size) = Utf8.DecodeRune(ustr, index, index - ustr.Length); var count = Rune.ColumnWidth(rune); - if (used + count >= width) break; + if (used + count > width) break; driver.AddRune(rune); used += count; index += size; diff --git a/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDetails.cs b/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDetails.cs index 2b4a6c7..4841b7f 100644 --- a/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDetails.cs +++ b/src/Microsoft.PowerShell.ConsoleGuiTools/GridViewDetails.cs @@ -8,7 +8,7 @@ internal class GridViewDetails // Contains the width of each column in the grid view. public int[] ListViewColumnWidths { get; set; } - // Dictates where the grid should actually start considering + // Dictates where the header should actually start considering // some offset is needed to factor in the checkboxes public int ListViewOffset { get; set; }