In this example we will create a simple form with a Combo Box, which will act as a drop down list. As an addition, we will add the functionality in the code to detect when the user selects anything from the drop down menu.
To create a simple PowerShell form, we can use the following code:
# Init PowerShell Gui
Add-Type -AssemblyName System.Windows.Forms
# Create a new form
$Form1 = New-Object system.Windows.Forms.Form
# Define the size, title and background color
$Form1.ClientSize = ‘300,250’
$Form1.text = “PowerShell GUI Example”
$Form1.BackColor = “#ffffff”
# Display the form
[void]$Form1.ShowDialog()
Once we run the above code, a simple window should be displayed:
Now lets take it a bit further and add a ComboBox. As mentioned, this will be our drop down list.
# Init PowerShell Gui
Add-Type -AssemblyName System.Windows.Forms
# Create a new form
$Form1 = New-Object system.Windows.Forms.Form
# Define the size, title and background color
$Form1.ClientSize = ‘300,250’
$Form1.text = “PowerShell GUI Example”
$Form1.BackColor = “#ffffff”
$List = New-Object system.Windows.Forms.ComboBox
$List.text = “”
$List.width = 170
$List.autosize = $true
# Add the items in the dropdown list
@(‘Jack’,’Dave’,’Alex’) | ForEach-Object {[void] $List.Items.Add($_)}
# Select the default value
$List.SelectedIndex = 0
$List.location = New-Object System.Drawing.Point(70,100)
$List.Font = ‘Microsoft Sans Serif,10’
$Form1.Controls.Add($List)
# Display the form
[void]$Form1.ShowDialog()
As you can see, our list contains 3 values: Jack, Dave and Alex. Once you run the above code, you should see the following window
Next, I added a label just to demonstrate how we will later on catch the selected index of the list. The last step is to add the actual index catch:
# Init PowerShell Gui
Add-Type -AssemblyName System.Windows.Forms
# Create a new form
$Form1 = New-Object system.Windows.Forms.Form
# Define the size, title and background color
$Form1.ClientSize = ‘300,250’
$Form1.text = “PowerShell GUI Example”
$Form1.BackColor = “#ffffff”
$List = New-Object system.Windows.Forms.ComboBox
$List.text = “”
$List.width = 170
$List.autosize = $true
# Add the items in the dropdown list
@(‘Jack’,’Dave’,’Alex’) | ForEach-Object {[void] $List.Items.Add($_)}
# Select the default value
$List.SelectedIndex = 0
$List.location = New-Object System.Drawing.Point(70,100)
$List.Font = ‘Microsoft Sans Serif,10’
#Add a label
$Description = New-Object system.Windows.Forms.Label
$Description.text = “Selected index: $selected”
$Description.AutoSize = $false
$Description.width = 450
$Description.height = 50
$Description.location = New-Object System.Drawing.Point(20,50)
$Description.Font = ‘Microsoft Sans Serif,10’
#Catch changes to the list
$List.add_SelectedIndexChanged({
$selected = $List.SelectedIndex
write-host $selected
$Description.text = “Selected index: $selected”
})
$Form1.Controls.Add($List)
$Form1.Controls.Add($Description)
# Display the form
[void]$Form1.ShowDialog()
The result of the above could should be something like this:
There is a very simple, but very useful control. It may
– be filled dynamically and manually
– accept user input (to disable user input is also possibly)
– pass its data to another control by user’s choice.
Well, let’s list what we are going to do with a combobox today:
1) accept value from a single textbox (by clicking a button)
2) accept values from multiple textboxes (from two of them by clicking a button)
3) accept user input and add it to the list (and discuss how to disable user input)
4) clear the list
5) use a value of user’s choise to set a value of one another control (the caption of the form)
6) Intellisense on user input
7) sorting items
If it’s enough, now turn to coding. Traditionally, the code bundle is attached in the box at right and it’s named, not surprisingly, HowToDealWithAComboBoxControl.zip.
The first our topic is how to accept user input. The following lines of code are taken from the $handler_button1_Click eventhandler:
$comboBox1.Items.Add($textBox1.Text); $comboBox1.Items.AddRange(($textBox1.Text, $textBox2.Text)); $comboBox1.Items.Add($comboBox1.Text);
In all three cases, data, usually of string type, is added by using such methods as Add(item) or AddRange(array of items). As can be seen, both methods are very easy to use.
Next, how we can prevent typing into a combobox? The answer is to set the DropDownStyle property:
$comboBox1.DropDownStyle = [System.Windows.Forms.ComboBoxStyle]::DropDownList;
After that, how to clean up our combobox?
$comboBox1.Items.Clear(); Next, how to grab a value from inside the user input?
$form1.Text = $comboBox1.Text;
How to sort data?
$comboBox1.Sorted = $true;
At last, how to use Intellisense? Please note, the DropDownStyle property should be set to System.Windows.Forms.ComboBoxStyle]::DropDown.
$comboBox1.AutoCompleteCustomSource.Add("System.Windows.Forms"); $comboBox1.AutoCompleteCustomSource.AddRange(("System.Data", "Microsoft")); $comboBox1.AutoCompleteMode = [System.Windows.Forms.AutoCompleteMode]::SuggestAppend; $comboBox1.AutoCompleteSource = [System.Windows.Forms.AutoCompleteSource]::CustomSource;
To test the Intellisense that is tuned above, type m or s in the combobox.
The whole sample is below:
#Generated Form Function function GenerateForm { ######################################################################## # Code Generated By: SAPIEN Technologies PrimalForms (Community Edition) v1.0.8.0 # Generated On: 21.07.2010 1:32 # Generated By: Administrator ######################################################################## #region Import the Assemblies [reflection.assembly]::loadwithpartialname("System.Windows.Forms") | Out-Null [reflection.assembly]::loadwithpartialname("System.Drawing") | Out-Null #endregion #region Generated Form Objects $form1 = New-Object System.Windows.Forms.Form $button1 = New-Object System.Windows.Forms.Button $button2 = New-Object System.Windows.Forms.Button $textBox2 = New-Object System.Windows.Forms.TextBox $textBox1 = New-Object System.Windows.Forms.TextBox $comboBox1 = New-Object System.Windows.Forms.ComboBox $InitialFormWindowState = New-Object System.Windows.Forms.FormWindowState #endregion Generated Form Objects #---------------------------------------------- #Generated Event Script Blocks #---------------------------------------------- #Provide Custom Code for events specified in PrimalForms. #region $handler_comboBox1_SelectedIndexChanged $handler_comboBox1_SelectedIndexChanged= { #TODO: Place custom script here try{ if ($comboBox1.Text.Length -gt 0) { $form1.Text = $comboBox1.Text; } }catch{} #in case no items are available } #endregion $handler_comboBox1_SelectedIndexChanged #region $handler_button1_Click $handler_button1_Click= { #TODO: Place custom script here try{ #How to add one item #$textBox1.Text if ($textBox1.Text.Length -gt 0 -and ` $textBox2.Text.Length -eq 0) { $comboBox1.Items.Add($textBox1.Text); Write-Host "Added " $textBox1.Text "from `$textBox1"; } #$textBox2.Text elseif ($textBox1.Text.Length -eq 0 -and ` $textBox2.Text.Length -gt 0) { $comboBox1.Items.Add($textBox2.Text); Write-Host "Added " $textBox2.Text "from `$textBox2"; } #$textBox1.Text and $textBox2.Text elseif ($textBox1.Text.Length -gt 0 -and ` $textBox2.Text.Length -gt 0) { $comboBox1.Items.AddRange(($textBox1.Text, $textBox2.Text)); Write-Host "Added " $textBox1.Text "from `$textBox1"; Write-Host "Added " $textBox2.Text "from `$textBox2"; } else { #Nothing to add #$textBox1.Text.Length -eq 0 #$textBox2.Text.Length -eq 0 } #At last, if the user typed something if ($comboBox1.Text.Length -gt 0) { $comboBox1.Items.Add($comboBox1.Text); Write-Host "Added " $comboBox1.Text "from `$comboBox1"; } }catch{} #for example, no data in the both textboxes } #endregion $handler_button1_Click #region $handler_button2_Click $handler_button2_Click= { #TODO: Place custom script here try{ #Clean up the combo box $comboBox1.Items.Clear(); $comboBox1.Text = ""; }catch{} } #endregion $handler_button2_Click $OnLoadForm_StateCorrection= {#Correct the initial state of the form to prevent the .Net maximized form issue $form1.WindowState = $InitialFormWindowState } #---------------------------------------------- #region Generated Form Code #region $form1 $form1.Text = "Primal Form" $form1.Name = "form1" $form1.DataBindings.DefaultDataSourceUpdateMode = 0 $System_Drawing_Size = New-Object System.Drawing.Size $System_Drawing_Size.Width = 282 $System_Drawing_Size.Height = 220 $form1.ClientSize = $System_Drawing_Size #endregion $form1 #region $button1 $button1.TabIndex = 3 $button1.Name = "button1" $System_Drawing_Size = New-Object System.Drawing.Size $System_Drawing_Size.Width = 70 $System_Drawing_Size.Height = 30 $button1.Size = $System_Drawing_Size $button1.UseVisualStyleBackColor = $True $button1.Text = "button1" $System_Drawing_Point = New-Object System.Drawing.Point $System_Drawing_Point.X = 195 $System_Drawing_Point.Y = 160 $button1.Location = $System_Drawing_Point $button1.DataBindings.DefaultDataSourceUpdateMode = 0 $button1.add_Click($handler_button1_Click) $form1.Controls.Add($button1) #endregion $button1 #region $button2 $button2.TabIndex = 4 $button2.Name = "button2" $System_Drawing_Size = New-Object System.Drawing.Size $System_Drawing_Size.Width = 70 $System_Drawing_Size.Height = 30 $button2.Size = $System_Drawing_Size $button2.UseVisualStyleBackColor = $True $button2.Text = "button2" $System_Drawing_Point = New-Object System.Drawing.Point $System_Drawing_Point.X = 15 $System_Drawing_Point.Y = 160 $button2.Location = $System_Drawing_Point $button2.DataBindings.DefaultDataSourceUpdateMode = 0 $button2.add_Click($handler_button2_Click) $form1.Controls.Add($button2) #endregion $button2 #region $textBox1 $System_Drawing_Size = New-Object System.Drawing.Size $System_Drawing_Size.Width = 250 $System_Drawing_Size.Height = 20 $textBox1.Size = $System_Drawing_Size $textBox1.DataBindings.DefaultDataSourceUpdateMode = 0 $textBox1.Name = "textBox1" $System_Drawing_Point = New-Object System.Drawing.Point $System_Drawing_Point.X = 15 $System_Drawing_Point.Y = 70 $textBox1.Location = $System_Drawing_Point $textBox1.TabIndex = 1 $form1.Controls.Add($textBox1) #endregion $textBox1 #region $textBox2 $System_Drawing_Size = New-Object System.Drawing.Size $System_Drawing_Size.Width = 250 $System_Drawing_Size.Height = 20 $textBox2.Size = $System_Drawing_Size $textBox2.DataBindings.DefaultDataSourceUpdateMode = 0 $textBox2.Name = "textBox2" $System_Drawing_Point = New-Object System.Drawing.Point $System_Drawing_Point.X = 15 $System_Drawing_Point.Y = 120 $textBox2.Location = $System_Drawing_Point $textBox2.TabIndex = 2 $form1.Controls.Add($textBox2) #endregion $textBox2 #region $comboBox1 $comboBox1.FormattingEnabled = $True $System_Drawing_Size = New-Object System.Drawing.Size $System_Drawing_Size.Width = 250 $System_Drawing_Size.Height = 21 $comboBox1.Size = $System_Drawing_Size $comboBox1.DataBindings.DefaultDataSourceUpdateMode = 0 $comboBox1.Name = "comboBox1" $System_Drawing_Point = New-Object System.Drawing.Point $System_Drawing_Point.X = 15 $System_Drawing_Point.Y = 20 $comboBox1.Location = $System_Drawing_Point $comboBox1.TabIndex = 0 $comboBox1.add_SelectedIndexChanged($handler_comboBox1_SelectedIndexChanged) $comboBox1.DropDownStyle = [System.Windows.Forms.ComboBoxStyle]::DropDown; $comboBox1.Sorted = $true; $comboBox1.AutoCompleteCustomSource.Add("System.Windows.Forms"); $comboBox1.AutoCompleteCustomSource.AddRange(("System.Data", "Microsoft")); $comboBox1.AutoCompleteMode = [System.Windows.Forms.AutoCompleteMode]::SuggestAppend; $comboBox1.AutoCompleteSource = [System.Windows.Forms.AutoCompleteSource]::CustomSource; $form1.Controls.Add($comboBox1) #endregion $comboBox1 #endregion Generated Form Code #Save the initial state of the form $InitialFormWindowState = $form1.WindowState #Init the OnLoad event to correct the initial state of the form $form1.add_Load($OnLoadForm_StateCorrection) #Show the Form $form1.ShowDialog()| Out-Null } #End Function #Call the Function GenerateForm
This post provides an example of using PowerShell to databind a combobox with a value and some text.
Creating a combobox in Powershell and adding an item to it is a relatively trivial task:
$combobox = New-Object System.Windows.Forms.ComboBox
$combobox.Items.add("alkane")
The text of the selected combobox can be obtained like so:
$combobox.Text
This is a combobox in its most simplistic form. The trouble is, I’m from an ASP.Net background and it’s often handy to bind a value (the hidden reference to the selected item – usually a primary key integer) AND some text (the value that the user sees in the combobox – the ‘friendly’ name). This requires a bit more leg work to implement and can be done by using a datatable, adding data to the datatable, and binding this datatable to our combobox like so:
[void][System.Reflection.Assembly]::LoadWithPartialName("System.Windows.Forms")
[void][System.Windows.Forms.Application]::EnableVisualStyles()
#create a form
$form = New-Object System.Windows.Forms.Form
#create a datatable to bind to our combobox
$datatable = New-Object system.Data.DataTable
#Define Columns
$col1 = New-Object system.Data.DataColumn "Value",([string])
$col2 = New-Object system.Data.DataColumn "Text",([string])
#add columns to datatable
$datatable.columns.add($col1)
$datatable.columns.add($col2)
#Create a row
$datarow1 = $datatable.NewRow()
#Enter data in the row
$datarow1.Value = "Example Value 1"
$datarow1.Text = "Example Text 1"
#Add the row to the datatable
$datatable.Rows.Add($datarow1)
#Create another row
$datarow2 = $datatable.NewRow()
#Enter data in the row
$datarow2.Value = "Example Value 2"
$datarow2.Text = "Example Text 2"
#Add the row to the datatable
$datatable.Rows.Add($datarow2)
#create a combobox
$combobox = New-Object System.Windows.Forms.ComboBox
$combobox.Add_SelectedIndexChanged({
#output the selected value and text
write-host $combobox.SelectedItem["Value"] $combobox.SelectedItem["Text"]
})
#clear combo before we bind it
$combobox.Items.Clear()
#bind combobox to datatable
$combobox.ValueMember = "Value"
$combobox.DisplayMember = "Text"
$combobox.Datasource = $datatable
#add combobox to form
$form.Controls.Add($combobox)
#show form
[void]$form.showdialog()
PowerShell GUI with buttons, textbox and combobox
GUI makes
life easier, but of course command line has a power of its own.
How to add a
form in PowerShell with Buttons, TextBox and ComboBox?
Adding GUI
forms in PowerShell must be done manually by code.
It’s not
that hard, you just need to love PowerShell and see what it can do to automate
IT administration and makes your life easier.
Anyway,
code below introduces how to add GUI to PowerShell and it also illustrates how
to make use of those GUI buttons and send a command to remote computers.
Code to add buttons, textbox and combobox in PowerShell, and how to execute a command after the button is clicked.
#initialize
the main form
$form = new-object Windows.forms.form
$form.text = «Server
Selection Form»
$form.minimumSize = New-Object System.Drawing.Size(600,300)
$form.maximumSize = New-Object System.Drawing.Size(600,300)
#add a button to the form
$button = new-object windows.forms.button
$button.text = «Close
Me»
#action that the button will execute after it has been clicked
$button.add_click({$form.close()})
#add a textbox to the form
$theTbox = New-Object system.Windows.Forms.Textbox
$theTbox.location = New-Object system.Drawing.Size(0,50)
$theTbox.size = New-Object System.Drawing.Size(100,20)
#add a drop down combobox to the form
$the_combo = New-Object system.Windows.Forms.ComboBox
$the_combo.location = New-Object system.Drawing.Size(0,90)
$the_combo.size = New-Object System.Drawing.Size(200,20)
$the_combo.DropDownStyle = «Dropdownlist»
#add another button to the form
$Go_button = new-object windows.forms.button
$Go_button.text = «Do
the Action»
$Go_button.location = New-Object system.Drawing.Size(0,190)
$Go_button.size = New-Object System.Drawing.Size(110,30)
#You can customized the command on this button
#Example below will shutdown the selected
computer
#Invoke-command for remote computer can also be used (imagination is your
friend 😊 )
$Go_button.add_click({Stop-Computer -ComputerName $theTbox.text})
#the “@” symbol will create an array out
of the text file contents
$ComboList_Items = Get-Content -Path @(«C:\dev\server_list.txt»)
#Loop thru the text file or the array
#and add the contents to the combobox for
selection
ForEach ($Server in $ComboList_Items) {
$the_combo.Items.Add($Server)
}
$form.controls.add($theTbox)
$form.controls.add($button)
$form.controls.add($Go_button)
$form.controls.add($the_combo)
$form.Add_shown({$form.Activate()})
#action that will capture every time a
value is selected on the combobox
$the_combo_SelectedIndexChanged=
{
$theTbox.text= $the_combo.text
}
$the_combo.add_SelectedIndexChanged($the_combo_SelectedIndexChanged)
$form.ShowDialog()
#===== CODE ends here ======
#The contents of the text file just look
like this:
Server-1
Server-2
Server-3
Server-4
Server-5
Server-6
Server-7
Localhost
Above
contents is the one that is being read by this line below, change the path and
the filename as necessary. It’s just for example purposes.
Cheers..till next time.
PowerShell Forms GUI allows users to create graphical user interfaces for their scripts, making it easier for users to interact with PowerShell commands through visual elements rather than the command line.
Here’s a simple code snippet to create a basic form in PowerShell:
Add-Type -AssemblyName System.Windows.Forms
$form = New-Object System.Windows.Forms.Form
$form.Text = 'My PowerShell GUI'
$form.Size = New-Object System.Drawing.Size(300,200)
$button = New-Object System.Windows.Forms.Button
$button.Location = New-Object System.Drawing.Point(100,70)
$button.Size = New-Object System.Drawing.Size(100,30)
$button.Text = 'Click Me'
$button.Add_Click({ [System.Windows.Forms.MessageBox]::Show('Hello, World!') })
$form.Controls.Add($button)
$form.ShowDialog()
Understanding Windows Forms
What is Windows Forms?
Windows Forms is a graphical (GUI) class library included as a part of the .NET Framework, allowing developers to create rich desktop applications. It provides a straightforward way to build user interfaces by offering a wide array of pre-defined controls. Since its introduction, Windows Forms has evolved to become a staple for developers looking to create traditional desktop applications for Windows.
Creating a Basic Windows Form
To get started with PowerShell Forms GUI, you first need to utilize the System.Windows.Forms namespace, which contains classes for building forms and controls. Here’s a simple code snippet to create a basic form:
Add-Type -AssemblyName System.Windows.Forms
$form = New-Object System.Windows.Forms.Form
$form.Text = "Hello World Form"
$form.ShowDialog()
This code initializes a basic Windows Form that simply displays a dialog with the title «Hello World Form.» The `ShowDialog()` method displays the form as a modal dialog box, blocking input to other windows until the form is closed.
Mastering PowerShell Format for Effortless Command Crafting
Designing a PowerShell GUI
Essential GUI Components
Common Controls are the building blocks of any GUI. Here’s a brief overview of some significant controls you’ll often use:
- Buttons: Triggers actions when clicked, such as executing commands or submitting forms.
- TextBoxes: Allows users to input text data.
- Labels: Displays static text or information that is read-only.
- ListBoxes: Displays a list of items from which users can select.
Layout Management
Effective layout management is crucial for usability. Various layout options like `FlowLayoutPanel` and `TableLayoutPanel` can help organize your controls neatly within the form. These layouts adjust dynamically based on the size and position of individual controls, improving the overall user experience.
Example: Building a Simple Calculator
Initial Setup
To illustrate how to create a more complex GUI, we’ll build a simple calculator. Here’s how to set up the initial form:
$form = New-Object System.Windows.Forms.Form
$form.Text = "Simple Calculator"
$form.Size = New-Object System.Drawing.Size(250, 200)
# Additional setup code will go here
Adding Controls
Next, we can add buttons and text boxes for our calculator functionality. For example, we’ll add two text boxes for input and a button for the addition operation.
$num1 = New-Object System.Windows.Forms.TextBox
$num2 = New-Object System.Windows.Forms.TextBox
$result = New-Object System.Windows.Forms.TextBox
$button = New-Object System.Windows.Forms.Button
$num1.Location = New-Object System.Drawing.Point(20, 20)
$num2.Location = New-Object System.Drawing.Point(20, 60)
$result.Location = New-Object System.Drawing.Point(20, 140)
$button.Location = New-Object System.Drawing.Point(20, 100)
$button.Text = "+"
$form.Controls.Add($num1)
$form.Controls.Add($num2)
$form.Controls.Add($result)
$form.Controls.Add($button)
Event Handling
Event handling is where PowerShell Forms really shines. You can make your application interactive by responding to user actions. Here’s how to handle the button click event:
$button.Add_Click({
$result.Text = [int]$num1.Text + [int]$num2.Text
})
This code will take the text from the two input text boxes, convert them into integers, and display the sum in the result text box when the button is clicked.
Customizing the Form
Styling and Appearance are important aspects of any GUI. You can enhance your form’s appearance by adjusting control properties, such as size, colors, and fonts:
$form.BackColor = [System.Drawing.Color]::LightGray
$button.BackColor = [System.Drawing.Color]::Green
$form.Size = New-Object System.Drawing.Size(300, 250)
Using Icons and Images is another way to make your application visually appealing. Setting an icon for your form can provide a professional touch:
$form.Icon = [System.Drawing.Icon]::ExtractAssociatedIcon("app.ico")
Mastering the PowerShell Formatter: A Quick Guide
Advanced Techniques
Integrating PowerShell Scripts with GUI
One of the most powerful features of a PowerShell Forms GUI is the capability to execute scripts from the GUI. For instance, you can run a PowerShell script when a specific action occurs, such as a button click.
Populating Data into Controls
Another advanced feature is dynamic data binding. You can populate a ListBox or ComboBox control with dynamic data from arrays or other data sources. Here’s how you would populate a ComboBox:
$comboBox = New-Object System.Windows.Forms.ComboBox
$comboBox.Location = New-Object System.Drawing.Point(20, 180)
$comboBox.Items.AddRange(@("Option 1", "Option 2", "Option 3"))
$form.Controls.Add($comboBox)
Validating User Input
Input validation is essential for maintaining the integrity of your application. When collecting user data, it’s important to ensure that the data entered meets the expected criteria:
if (-not $num1.Text -or -not $num2.Text) {
[System.Windows.Forms.MessageBox]::Show("Both fields must be filled!")
}
Using MessageBox to display alerts can help inform users about input errors effectively.
PowerShell Format Number: Essentials Made Easy
Debugging and Error Handling
Common Errors in PowerShell GUI
While working with PowerShell Forms, you might encounter typical pitfalls, such as control placement issues or incorrect data types. Understanding these issues can save you time during development.
Implementing Error Handling
To create a smooth user experience, implementing error handling using try-catch blocks is crucial:
try {
# Code that may cause an exception
$result.Text = [int]$num1.Text + [int]$num2.Text
} catch {
[System.Windows.Forms.MessageBox]::Show("An error occurred: $_")
}
This ensures that your application handles unexpected issues gracefully, providing valuable feedback to users rather than crashing.
Mastering PowerShell ToString: Quick Conversion Guide
Conclusion
In summary, creating a PowerShell Forms GUI allows you to develop rich, interactive applications that make use of PowerShell’s powerful scripting capabilities. From creating simple forms and controls to implementing advanced features like event handling and dynamic data binding, the possibilities are vast.
As you experiment with these techniques, don’t be afraid to think creatively and challenge yourself. Each project you undertake builds your skills further. For ongoing learning, explore the wealth of resources available such as books, tutorials, and online communities centered around PowerShell.
By starting today, you can create beautiful and functional GUIs that not only enhance your automation scripts but also broaden your capabilities as a developer in the PowerShell ecosystem. Happy scripting!