PowerShell Scripts, Tips, Expert Advices, Forums, and Resources

Geek Sync Live

Welcome to PowerShell.com, the educational and community site for Windows PowerShell People. Get a quick overview.


As a Powershell.com member you will have access to:

  • Daily PowerShell tips written by Microsoft MVPs and other leading Windows PowerShell experts
  • Free Windows PowerShell advice and training provided by Microsoft MVPs and other leading Windows PowerShell experts
  • Access to leading Windows PowerShell blogs
  • A free ebook, Mastering PowerShell, written by Microsoft MVP Dr. Tobias Weltner
PowerTip of the Day

Using PowerShell’s Help Window for General Output

To display text information, you can of course launch notepad.exe, and use the editor to display the text. Displaying text in an editor is not such a good idea, though, if you want to make sure the text cannot be changed.

PowerShell comes with a great window to display small and medium size texts: the built-in Help window.

With a little tweaking, this window can be reprogrammed to display just about any kind of text information. What's more, you can use the built-in full text search capabilities to navigate in your text, and even set foreground and background color as you like.

Just pipe any text you want displayed to Out-Window, and optionally specify colors, search word, and title. Here is the Out-Window function:

function Out-Window
{
  param
  (
    [String]
    $Title = 'PowerShell Output',

    [String]
    $FindText = '',

    [String]
    $ForegroundColor = 'Black',

    [String]
    $BackgroundColor = 'White'
  )
  
  # take all pipeline input:
  $allData = @($Input)
  
  if ($allData.Count -gt 0)
  {
    # open window in new thread to keep PS responsive
    $code = {
      param($textToDisplay, $FindText, $Title, $ForegroundColor, $BackgroundColor)

      $dialog = (New-Object TypeName Microsoft.Management.UI.HelpWindow($textToDisplay))
      $dialog.Title = $Title
      $type = $dialog.GetType()
      $field = $type.GetField('Settings', 'NonPublic,Instance')
      $button = $field.GetValue($dialog)
      $button.Visibility = 'Collapsed'
      $dialog.Show()
      $dialog.Hide()
      $field = $type.GetField('Find', 'NonPublic,Instance')
      $textbox = $field.GetValue($dialog)
      $textbox.Text = $FindText
      $field = $type.GetField('HelpText', 'NonPublic,Instance')
      $RTB = $field.GetValue($dialog)
      $RTB.Background = $BackgroundColor
      $RTB.Foreground = $ForegroundColor
      $method = $type.GetMethod('MoveToNextMatch', [System.Reflection.BindingFlags]'NonPublic,Instance')
      $method.Invoke($dialog, @($true))
      $dialog.ShowDialog()
    }
      
    $ps = [PowerShell]::Create()
    $newRunspace = [RunSpaceFactory]::CreateRunspace()
    $newRunspace.ApartmentState = 'STA'
    $newRunspace.Open()
      
      
    $ps.Runspace = $newRunspace
    $null = $ps.AddScript($code).AddArgument(($allData | Format-Table -AutoSize -Wrap | Out-String -Width 100)).AddArgument($FindText).AddArgument($Title).AddArgument($ForegroundColor).AddArgument($BackgroundColor)
    $null = $ps.BeginInvoke()      
  }
}

This is what a sample call could look like:

Get-Content C:\Windows\windowsupdate.log  |  
  # limit to first 100 lines (help window is not designed to work with huge texts)
  Select-Object -First 100 |
  Out-Window -Find Success -Title 'My Output' -Background Blue -Foreground White

Keep two things in mind:

  • The help window is not designed to display huge texts. Make sure you use this approach for texts that do not exceed a couple of kilobytes
  • This is just experimental code. There is no clean up of the PowerShell thread spawned to display the window. When you close the window, the PowerShell thread will stay around until you close PowerShell. What needs to be added is an event handler that fires when the help window closes. This event handler could then clean up the PowerShell thread.

 

Twitter This Tip! ReTweet this Tip!

Copyright 2012 PowerShell.com. All rights reserved.