Ironman Software Forums
Continue the conversion on the Ironman Software forums. Chat with over 1000 users about PowerShell, PowerShell Universal, and PowerShell Pro Tools.
In this post, we’ll look at how to create a Out-TreeView
cmdlet with Terminal.GUI
.
The GUI.CS project is a terminal interface library for .NET. It has many controls for building user interfaces in .NET applications. We use this library for the TUI Designer.
It has controls such as:
To use GUI.CS in PowerShell, you will need to download the appropriate binaries from NuGet. NuGet packages are just ZIP files. You can download an rename them to ZIP to access the files within them.
Invoke-WebRequest https://www.nuget.org/api/v2/package/Terminal.Gui/1.3.1 -OutFile .\terminal.gui.zip
Within the lib
folder you will find binaries for different platforms. For the purposes of this blog post, we’ll use the netstandard2.0
binary.
You will also need the NStack library as Terminal.Gui relies on it.
Invoke-WebRequest https://www.nuget.org/api/v2/package/NStack.Core/0.16.0 -OutFile .\nstack.zip
Once the binaries have been downloaded, you will need to copy the NStack.dll
and the Terminal.Gui.dll
into a folder. You can load the binaries using Import-Module
and call the Terminal.Gui
classes from PowerShell.
[Terminal.Gui.Application]::Init()
$Top = [Terminal.Gui.Application]::Top
$Win = [Terminal.Gui.Window]::new("Hello, World!")
$Win.Height = [Terminal.Gui.Dim]::Fill()
$Win.Width = [Terminal.Gui.Dim]::Fill()
$Top.Add($Win)
[Terminal.Gui.Application]::Run()
The Out-TreeView
cmdlet will use the Terminal.Gui classes and pipeline input in PowerShell to output a treeview based on the objects defined.
The following script loads the binaries and defines the Out-TreeView
cmdlet to output a tree view based on objects.
Import-Module "$PSScriptRoot\Gui\NStack.dll" | Out-Null
Import-Module "$PSScriptRoot\Gui\Terminal.Gui.dll" | Out-Null
function Expand-Object {
[CmdletBinding()]
param(
[Parameter(Mandatory, ValueFromPipeline)]
[object]$InputObject
)
Process {
if ($InputObject -eq $null) {
return
}
$InputObject | Get-Member -MemberType Properties | ForEach-Object {
try {
$Value = $InputObject.($_.Name)
$Node = [Terminal.Gui.Trees.TreeNode]::new("$($_.Name) = $Value")
if ($Value -ne $null) {
$Children = Expand-Object -InputObject $Value
foreach ($child in $Children) {
$Node.Children.Add($child)
}
}
$Node
}
catch {
Write-Host $_
}
}
}
}
function Out-TreeView {
[CmdletBinding()]
param(
[Parameter(Mandatory, ValueFromPipeline)]
[object]$InputObject
)
Begin {
$Objects = @()
}
Process {
$Objects += $InputObject
}
End {
[Terminal.Gui.Application]::Init()
$Top = [Terminal.Gui.Application]::Top
$Win = [Terminal.Gui.Window]::new("Out-TreeView")
$Win.Height = [Terminal.Gui.Dim]::Fill()
$Win.Width = [Terminal.Gui.Dim]::Fill()
$TreeView = [Terminal.Gui.TreeView]::new()
$TreeView.Height = [Terminal.Gui.Dim]::Fill()
$TreeView.Width = [Terminal.Gui.Dim]::Fill()
foreach ($item in $Objects) {
$root = [Terminal.Gui.Trees.TreeNode]::new($item.GetType().Name)
$Children = Expand-Object $item
$Children | ForEach-Object {
$root.Children.Add($_)
}
$TreeView.AddObject($root)
}
$Win.Add($TreeView)
$Top.Add($Win)
[Terminal.Gui.Application]::Run()
}
}
Once you’ve defined the above cmdlet, you can use it on the pipeline.
Get-Process | Select-Object -First 10 | Out-TreeView
The Out-TreeView
cmdlet can be used to view complex objects using Terminal.Gui. The cmdlet likely could be improved to increase performance and lazy load properties.
Find this useful? Please consider sharing this article. Have a question about PowerShell? Contact us and we'll write a post about it.
Continue the conversion on the Ironman Software forums. Chat with over 1000 users about PowerShell, PowerShell Universal, and PowerShell Pro Tools.
Receive once-a-month updates about Ironman Software. You'll learn about our product updates and blogs related to PowerShell.