# encoding: ascii
# api: powershell
# title: Write-ProgressForm
# description: GUI Replacement for PowerShell’s Write-Progress command
# version: 1.0
# type: function
# author: Denis St-Pierre
# license: CC0
# function: Write-ProgressForm
# x-poshcode-id: 4019
# x-archived: 2014-04-17T20:21:22
# x-published: 2014-03-15T17:27:00
#
# Uses same named parameters for drop-in replacement
# CAVEATS: You can’t close the Form by clicking on it, must call Write-ProgressForm -Completed
# Code below is a working sample
#
function Write-ProgressForm {
	<#
	.SYNOPSIS
		Write-ProgressForm V1.0
		GUI Replacement for PowerShell's Write-Progress command

	.DESCRIPTION
		GUI Replacement for PowerShell's Write-Progress command
		Uses same named parameters for drop-in replacement
		CAVEATS: You can't close the Form by clicking on it, must call Write-ProgressForm -Completed
				 Therefore decided to hide Close button (why tease people?)

	.INPUTS
		Same as Write-Progress command 
		BONUS:
		-ICOpath <path to your ICO>
		-FormTitle <Title of the Write-progress form> 
		(Only needs to be mentioned when 1st called then it sticks around)
		
	.OUTPUTS
		Nothing but a GUI

	.NOTES
		Uses Global variables extensively
		License: GPL v3.0 or greater / BSD (Latest version)
		Form Code Generated By: SAPIEN Technologies PrimalForms (Community Edition) v1.0.10.0
		Generated On: 30/01/2013 12:38 PM
		Generated By: Denis St-Pierre, Ottawa, Canada
	#>
	
	param(	#parameters with default values assigned
		[String]$Activity="Activity",
		[String]$CurrentOperation="CurrentOperation",
		[String]$status="Status",
		[Int]$PercentComplete=0,
		[switch]$Completed=$false,
		[int]$FontSize = 10,
		[String]$ICOpath="",	#yes, you can use your *OWN* icon file in the form
		[String]$FormTitle=""
		
	)
	
	$HideUselessCloseButton=$true	#Change to false if you can fix it, pls
	$UselessAutoSize=$false			#Useless because it doesn't work as expected
	
	#If WriteProgressForm variable exists, use it.
	If ( Get-Variable -Name WriteProgressForm -Scope Global -ErrorAction SilentlyContinue ) {
		If ( $Completed){	#If asked to close, do it
			$progressBar1.Value=100
			$StatusLabel.Text = "Complete"
			Start-Sleep -Seconds 1
			$WriteProgressForm.close()
			Return
		} else {		#otherwise, Update it
			$progressBar1.Value = $PercentComplete	#To update Progress bar position
			$ActivityLabel.Text = "$Activity"
			$CurrentOperationLabel.Text = "$CurrentOperation"
			$StatusLabel.Text = "$status"
			Return
		}
	}

	#region Import the Assemblies
	[reflection.assembly]::loadwithpartialname("System.Windows.Forms") | Out-Null
	[reflection.assembly]::loadwithpartialname("System.Drawing") | Out-Null
	#endregion

	#region Generated Form Objects
	$global:WriteProgressForm = New-Object System.Windows.Forms.Form
	$global:StatusLabel = New-Object System.Windows.Forms.Label
	$CloseButton = New-Object System.Windows.Forms.Button
	$global:progressBar1 = New-Object System.Windows.Forms.ProgressBar
	$global:CurrentOperationLabel = New-Object System.Windows.Forms.Label
	$global:ActivityLabel = New-Object System.Windows.Forms.Label
	$InitialFormWindowState = New-Object System.Windows.Forms.FormWindowState
	#endregion Generated Form Objects

	#----------------------------------------------
	#Generated Event Script Blocks
	#----------------------------------------------
	#Provide Custom Code for events specified in PrimalForms.
#	$WriteProgressForm.close()= 
#	{
	#TODO: Place custom script here	
#	}

	$CloseButton_OnClick= 
	{
	#TODO: Place custom script here

	}

	$OnLoadForm_StateCorrection=
	{#Correct the initial state of the form to prevent the .Net maximized form issue
		$WriteProgressForm.WindowState = $InitialFormWindowState
	}

	#----------------------------------------------
	#region Generated Form Code
	$WriteProgressForm.AccessibleDescription = "WriteProgressFormDesc"
	$WriteProgressForm.AccessibleName = "WriteProgressForm"
	$WriteProgressForm.AccessibleRole = 48
	$WriteProgressForm.AutoSize = $true		#works on forms, labels not so much
	$WriteProgressForm.AutoSizeMode = 0
	$System_Drawing_Size = New-Object System.Drawing.Size
#	$System_Drawing_Size.Height = 170
#	$System_Drawing_Size.Width = 505
#	$WriteProgressForm.ClientSize = $System_Drawing_Size
	$WriteProgressForm.DataBindings.DefaultDataSourceUpdateMode = 0
	$WriteProgressForm.StartPosition = 1 #Center of the Screen
	#add Icon to dialog, if possible
	If ( ($ICOpath -ne "") -and (Test-Path "$ICOpath") ) {
		Try {	#If the ICO file is NFG, ignore and move on
			$WriteProgressForm.Icon = [System.Drawing.Icon]::ExtractAssociatedIcon("$ICOpath")
		} catch { } #use default ICO
	}
	$WriteProgressForm.Name = "WriteProgressForm"
	$WriteProgressForm.Text = "$FormTitle"
#	$WriteProgressForm.add_FormClosing($WriteProgressForm.close()) #failed attempt to make CloseButton work w/o PS code

	# ** $StatusLabel
	$StatusLabel.DataBindings.DefaultDataSourceUpdateMode = 0
	$System_Drawing_Point = New-Object System.Drawing.Point
	$System_Drawing_Point.X = 15
	$System_Drawing_Point.Y = 33
	$StatusLabel.Location = $System_Drawing_Point
	$System_Drawing_Size = New-Object System.Drawing.Size
	$System_Drawing_Size.Height = 20
	$System_Drawing_Size.Width = 475
	$StatusLabel.MinimumSize = $System_Drawing_Size
	$StatusLabel.AutoSize = $UselessAutoSize
	$StatusLabel.Name = "StatusLabel"
	$System_Windows_Forms_Padding = New-Object System.Windows.Forms.Padding
	$System_Windows_Forms_Padding.All = 1
	$System_Windows_Forms_Padding.Bottom = 1
	$System_Windows_Forms_Padding.Left = 1
	$System_Windows_Forms_Padding.Right = 1
	$System_Windows_Forms_Padding.Top = 1
	$StatusLabel.Padding = $System_Windows_Forms_Padding
#	$System_Drawing_Size = New-Object System.Drawing.Size
#	$System_Drawing_Size.Height = 20
#	$System_Drawing_Size.Width = 475
#	$StatusLabel.Size = $System_Drawing_Size
	$StatusLabel.TabIndex = 4
	$StatusLabel.Text = "$status"
	
	$WriteProgressForm.Controls.Add($StatusLabel)
	
	# ** $CloseButton
	$CloseButton.DataBindings.DefaultDataSourceUpdateMode = 0
	$System_Drawing_Point = New-Object System.Drawing.Point
	$System_Drawing_Point.X = 400
	$System_Drawing_Point.Y = 134
	$CloseButton.Location = $System_Drawing_Point
	$CloseButton.Name = "CloseButton"
	$System_Drawing_Size = New-Object System.Drawing.Size
	$System_Drawing_Size.Height = 25
	$System_Drawing_Size.Width = 90
	$CloseButton.Size = $System_Drawing_Size
	$CloseButton.TabIndex = 3
	$CloseButton.Text = "Close"
	$CloseButton.UseVisualStyleBackColor = $True
	$CloseButton.add_Click($CloseButton_OnClick)
#	$CloseButton.add_MouseClick($WriteProgressForm.close()) #failed attempt #2 to make CloseButton work w/o PS code
	
	If ($HideUselessCloseButton) {
		#dont add button to form
	} else {
		$WriteProgressForm.Controls.Add($CloseButton)
	}
	
	# ** $progressBar1
	$progressBar1.DataBindings.DefaultDataSourceUpdateMode = 0
	$System_Drawing_Point = New-Object System.Drawing.Point
	$System_Drawing_Point.X = 10
	$System_Drawing_Point.Y = 57
	$progressBar1.Location = $System_Drawing_Point
	$System_Windows_Forms_Padding = New-Object System.Windows.Forms.Padding
	$System_Windows_Forms_Padding.All = 5
	$System_Windows_Forms_Padding.Bottom = 5
	$System_Windows_Forms_Padding.Left = 5
	$System_Windows_Forms_Padding.Right = 5
	$System_Windows_Forms_Padding.Top = 5
	$progressBar1.Margin = $System_Windows_Forms_Padding
	$System_Drawing_Size = New-Object System.Drawing.Size
	$System_Drawing_Size.Height = 30
	$System_Drawing_Size.Width = 480
	$progressBar1.MinimumSize = $System_Drawing_Size
	$progressBar1.AutoSize = $UselessAutoSize	#doesn't work, stays the same size
	$progressBar1.Name = "progressBar1"
#	$System_Drawing_Size = New-Object System.Drawing.Size
#	$System_Drawing_Size.Height = 30
#	$System_Drawing_Size.Width = 480
#	$progressBar1.Size = $System_Drawing_Size
	$progressBar1.Step = 1
	$progressBar1.Style = 1
	$progressBar1.TabIndex = 2
	$progressBar1.Value = $PercentComplete	#Progress bar position
	
	$WriteProgressForm.Controls.Add($progressBar1)
	
	# ** $CurrentOperationLabel
	$CurrentOperationLabel.AccessibleDescription = "CurrentOperationDesc"
	$CurrentOperationLabel.AccessibleName = "CurrentOperation"
	$CurrentOperationLabel.AccessibleRole = 0
	$CurrentOperationLabel.CausesValidation = $False
	$CurrentOperationLabel.DataBindings.DefaultDataSourceUpdateMode = 0
	$System_Drawing_Point = New-Object System.Drawing.Point
	$System_Drawing_Point.X = 15
	$System_Drawing_Point.Y = 100
	$CurrentOperationLabel.Location = $System_Drawing_Point
	$System_Windows_Forms_Padding = New-Object System.Windows.Forms.Padding
	$System_Windows_Forms_Padding.All = 1
	$System_Windows_Forms_Padding.Bottom = 1
	$System_Windows_Forms_Padding.Left = 1
	$System_Windows_Forms_Padding.Right = 1
	$System_Windows_Forms_Padding.Top = 1
	$CurrentOperationLabel.Margin = $System_Windows_Forms_Padding
	$System_Drawing_Size = New-Object System.Drawing.Size
	$System_Drawing_Size.Height = 20
	$System_Drawing_Size.Width = 475
	$CurrentOperationLabel.MinimumSize = $System_Drawing_Size
	$CurrentOperationLabel.AutoSize = $UselessAutoSize
	$CurrentOperationLabel.Name = "CurrentOperationLabel"
	$System_Windows_Forms_Padding = New-Object System.Windows.Forms.Padding
	$System_Windows_Forms_Padding.All = 1
	$System_Windows_Forms_Padding.Bottom = 1
	$System_Windows_Forms_Padding.Left = 1
	$System_Windows_Forms_Padding.Right = 1
	$System_Windows_Forms_Padding.Top = 1
	$CurrentOperationLabel.Padding = $System_Windows_Forms_Padding
#	$System_Drawing_Size = New-Object System.Drawing.Size
#	$System_Drawing_Size.Height = 20
#	$System_Drawing_Size.Width = 475
#	$CurrentOperationLabel.Size = $System_Drawing_Size
	$CurrentOperationLabel.TabIndex = 1
	$CurrentOperationLabel.Text = "$CurrentOperation"
	
	$WriteProgressForm.Controls.Add($CurrentOperationLabel)
	
	# ** $ActivityLabel
#	$ActivityLabel.CausesValidation = $False
	$ActivityLabel.DataBindings.DefaultDataSourceUpdateMode = 0
	$System_Drawing_Point = New-Object System.Drawing.Point
	$System_Drawing_Point.X = 10
	$System_Drawing_Point.Y = 10
	$ActivityLabel.Location = $System_Drawing_Point
	$System_Windows_Forms_Padding = New-Object System.Windows.Forms.Padding
	$System_Windows_Forms_Padding.All = 1
	$System_Windows_Forms_Padding.Bottom = 1
	$System_Windows_Forms_Padding.Left = 1
	$System_Windows_Forms_Padding.Right = 1
	$System_Windows_Forms_Padding.Top = 1
	$ActivityLabel.Margin = $System_Windows_Forms_Padding
	$System_Drawing_Size = New-Object System.Drawing.Size
	$System_Drawing_Size.Height = 20
	$System_Drawing_Size.Width = 480
	$ActivityLabel.MinimumSize = $System_Drawing_Size
	$ActivityLabel.Name = "ActivityLabel"
	$System_Windows_Forms_Padding = New-Object System.Windows.Forms.Padding
	$System_Windows_Forms_Padding.All = 1
	$System_Windows_Forms_Padding.Bottom = 1
	$System_Windows_Forms_Padding.Left = 1
	$System_Windows_Forms_Padding.Right = 1
	$System_Windows_Forms_Padding.Top = 1
	$ActivityLabel.Padding = $System_Windows_Forms_Padding
	$ActivityLabel.AutoSize = $UselessAutoSize
#	$System_Drawing_Size = New-Object System.Drawing.Size
#	$System_Drawing_Size.Height = 20
#	$System_Drawing_Size.Width = 480
#	$ActivityLabel.Size = $System_Drawing_Size
	$ActivityLabel.TabIndex = 0
	$ActivityLabel.Font = New-Object System.Drawing.Font("Microsoft Sans Serif",$FontSize,1,3,1)
	$ActivityLabel.Text = "$Activity"

	$WriteProgressForm.Controls.Add($ActivityLabel)

	#endregion Generated Form Code

	#Save the initial state of the form
	$InitialFormWindowState = $WriteProgressForm.WindowState
	#Init the OnLoad event to correct the initial state of the form
	$WriteProgressForm.add_Load($OnLoadForm_StateCorrection)
	
	#Show the Form
#	$WriteProgressForm.ShowDialog()| Out-Null #ShowDialog waits until it is closed
	$WriteProgressForm.Show()		#show form and keep on going
	$WriteProgressForm.activate()	#Make sure its on top
	Start-sleep -Milliseconds 500	#was needed to give time for form to fully draw itself
} #End Function


#Clean up global WriteProgressForm variables before 
try {
	$WriteProgressForm.close()
	Remove-Variable StatusLabel | Out-Null
	Remove-Variable CurrentOperationLabel | Out-Null
	Remove-Variable progressBar1 | Out-Null
	Remove-Variable ActivityLabel | Out-Null
	Remove-Variable WriteProgressForm
} catch {
	#go on
}

$ScopeNum=0
$Scope=0
$TotalNumScopes=100
	
#Foreach ($DHCPScope in $ObjDHCPscopes){
for ($PCcomplete=1; $PCcomplete -lt 100; $PCcomplete++) {
	$ScopeName="ScopeName"
	$Scope=$Scope+1	#increment
	$CurrentOperation="*CurOp*Getting Leases from scope $ScopeName"
	$Status="*Status*$PCcomplete% complete. ($Scope of $TotalNumScopes)"
#	Write-Progress -Activity "*Act*Building list from DHCP server ..." -status $status -PercentComplete $PCcomplete -CurrentOperation "$CurrentOperation"
	Write-ProgressForm -Activity "*Act*Building list from DHCP server ... Building list from DHCP server... Building list from DHCP server ..." -status $status -PercentComplete $PCcomplete -CurrentOperation "$CurrentOperation"
	Start-sleep -Milliseconds 050
	
}
$PCcomplete=100
$CurrentOperation="complete"
#Write-Progress -Activity "Building list from DHCP server ..." -PercentComplete $PCcomplete -CurrentOperation "$CurrentOperation" -Status "$PCcomplete% complete."
Write-ProgressForm -Activity "Building list from DHCP server ..." -PercentComplete $PCcomplete -CurrentOperation "$CurrentOperation" -Status "$PCcomplete% complete."
Start-sleep -seconds 1
#Write-Progress -Activity "Complete" -Completed -Status "Complete" 
Write-ProgressForm -Activity "Complete" -Completed -Status "Complete"
