today12
Goto Top

Powershell progressbar AND multitask

Hallo Leute,

ich bin mal wieder auf eure Hilfe angewiesen, da mir die verschiedensten SuFu keine geeigneten Ergebnisse liefern können.

Ich arbeite hier mit SAPIEN Powershell Studio 2012.
Es soll eigentlich nicht mehr können, als dass man den "Abbruch"-Button (dtz. noch nicht belegt. ) verwenden kann, während die Progressbar bis 15 zählt.
Geklickt kann innerhalb der GUI erst dann wieder werden, wenn dieser "Progressbar"-Prozess abgeschlossen ist.

Wie kann ich das am besten Umsetzen ? Gibt es da etwas wie Multithreading/Multiprocessing innerhalb dieser Oberfläche ?

Vielen Dank schon Mal.

559e2488a4dd44afcc99aa0d8c55b45b

ed92407d34c5cbeefda88e5ac069e402

LG

Content-ID: 263224

Url: https://administrator.de/contentid/263224

Ausgedruckt am: 22.11.2024 um 03:11 Uhr

colinardo
colinardo 12.02.2015 aktualisiert um 20:31:49 Uhr
Goto Top
Hallo today12,
Lösungen dazu findest du hier:

Falls dir die Codes aus den obigen Threads zu schwer sein sollten, hier noch eine einfache Variante mit einem Timer welcher die Progressbar aktualisiert:
#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
$progress = New-Object System.Windows.Forms.ProgressBar
$InitialFormWindowState = New-Object System.Windows.Forms.FormWindowState
$timer = New-Object System.Windows.Forms.Timer
#endregion Generated Form Objects

$global:cnt = 0

$handler_button1_Click= {
    if ($button1.Text -eq "Start"){  
        $global:cnt = 0
        $timer.Start()
        $button1.Text = "Stop"  
    }else{
        $timer.Stop()
        $button1.Text = "Start"  
    }

}
$handler_tick = {
    if ($global:cnt -le 100) {
        $progress.Value = $global:cnt++
    }else{
        $timer.Enabled = $false
        $button1.Text = "Start"  
    }
}

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

#----------------------------------------------
#region Generated Form Code
$System_Drawing_Size = New-Object System.Drawing.Size
$System_Drawing_Size.Height = 74
$System_Drawing_Size.Width = 292
$form1.ClientSize = $System_Drawing_Size
$form1.DataBindings.DefaultDataSourceUpdateMode = 0
$form1.MaximizeBox = $False
$form1.Name = "form1"  
$form1.Text = "ProgressForm"  


$button1.DataBindings.DefaultDataSourceUpdateMode = 0

$System_Drawing_Point = New-Object System.Drawing.Point
$System_Drawing_Point.X = 12
$System_Drawing_Point.Y = 41
$button1.Location = $System_Drawing_Point
$button1.Name = "button1"  
$System_Drawing_Size = New-Object System.Drawing.Size
$System_Drawing_Size.Height = 23
$System_Drawing_Size.Width = 268
$button1.Size = $System_Drawing_Size
$button1.TabIndex = 1
$button1.Text = "Start"  
$button1.UseVisualStyleBackColor = $True
$button1.add_Click($handler_button1_Click)

$form1.Controls.Add($button1)

$progress.DataBindings.DefaultDataSourceUpdateMode = 0
$System_Drawing_Point = New-Object System.Drawing.Point
$System_Drawing_Point.X = 12
$System_Drawing_Point.Y = 12
$progress.Location = $System_Drawing_Point
$progress.Name = "progress"  
$System_Drawing_Size = New-Object System.Drawing.Size
$System_Drawing_Size.Height = 23
$System_Drawing_Size.Width = 268
$progress.Size = $System_Drawing_Size
$progress.TabIndex = 0

$form1.Controls.Add($progress)

#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)

#Timer settings
$timer.add_tick($handler_tick)
$timer.Enabled = $false
$timer.Interval = 50

#----- Show Form
$form1.ShowDialog() | out-null

# WICHTIG Timer resourcen freigeben 
$timer.dispose()
Grüße Uwe
today12
today12 12.02.2015 um 20:44:32 Uhr
Goto Top
Danke schonmal für die Hilfe :D
Ich hab aber hier bei dieser Schleife doch noch das ein oder andere Verständnis Problem::

$proc = $true

while(!$proc.HasExited)
{
$time = 15 # seconds, use you actual time in here
foreach($i in (1..$time)) {
$percentage = $i / $time
$progressbar1.Value = ($percentage * 100)
Start-Sleep 1
}

Wsl. hab ich das eh falsch interpretiert
aber wie kann ich das anhand dieser Schleife ermöglichen, dass damit nur die Progessbar angeprochen wird ?!

:
114757
114757 13.02.2015 aktualisiert um 08:29:58 Uhr
Goto Top
Wsl. hab ich das eh falsch interpretiert
aber wie kann ich das anhand dieser Schleife ermöglichen, dass damit nur die Progessbar angeprochen wird ?!
Diese Schleife bringt dich keinen Schritt weiter wenn du sie nicht aus einem anderen Thread laufen lässt denn sonst blockiert diese ebenfalls den Userthread für mögliche Eingaben !!

Nutze die einfache Variante von @colinardo oben mit dem Timer, dort wird die ProgressBar nämlich aus dem Eventhandler in einem parallelthread aktualisiert ! Fortgeschrittene wählen natürlich die Runspace-Methode aus dem ersten Link.

Gruß jodel32
colinardo
colinardo 13.02.2015 um 09:52:27 Uhr
Goto Top
Da kann ich @114757 nur beipflichten. Mit dieser Schleife erreichst du nicht dein Ziel, weil sie eben wie schon geschrieben den Userthread blockiert und damit die User-Interaktion mit den Steuerelementen.

Grüße Uwe