- $count is an index of element from array of processes
- when the current process has exited i simply do: $script:count++
- SynchronizingObject has to be passed via parameter to the function
- it's possible to send input to the current app
- readinput process is readinput.exe from below code
It seems to behave exactly as I wanted. Let me integrate it and see final results. Amazing support by jvierra, thank you!
code for readinput.exe
Code: Select all
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace readinput {
class Program {
static void Main( string[] args ) {
Console.WriteLine("Read input");
Console.WriteLine("");
var s = Console.ReadLine();
Console.WriteLine("Out from app:");
Console.WriteLine(s);
//Console.ReadKey();
}
}
}
Code: Select all
$code = @'
[DllImport("user32.dll", SetLastError = true)]
public static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent);
'@
Add-Type -MemberDefinition $code -Name Win32SetParent -Namespace Win32Functions
function Run-Process ($count, $sync) {
$script:p = [System.Diagnostics.Process]::New() # has to be $script: because of buttonSendInput_Click > $p.StandardInput.WriteLin
$p.add_Exited({
#[System.Windows.Forms.MessageBox]::Show('Process Exited!')
$script:count++
if ($script:count -lt $dataP.count) {
Run-Process -count $script:count -sync $form1
}
})
$p.add_OutputDataReceived({
$textbox2.Lines += $_.Data
$textbox2.Select($textbox2.Text.Length, 0)
$textbox2.ScrollToCaret()
})
$p.StartInfo.RedirectStandardOutput = $true
$p.StartInfo.RedirectStandardError = $true
$p.StartInfo.RedirectStandardInput = $true
$p.StartInfo.UseShellExecute = $false
#$p.StartInfo.CreateNoWindow = $true
$p.StartInfo.FileName = $dataP[$count]
$p.StartInfo.Arguments = '-n 3 google.com'
$p.EnableRaisingEvents = $true
$p.SynchronizingObject = $sync
if ($script:count -lt $dataP.count) {
$p.Start()
do {
Start-Sleep -Milliseconds 50
} until ($p.MainWindowHandle)
$p.BeginOutputReadLine()
[Win32Functions.Win32SetParent]::SetParent($p.MainWindowHandle, $textbox1.Handle)
}
}
$form1_Load = {
#TODO: Initialize Form Controls here
$global:dataP = 'ping', 'readinput', 'ping'
$script:count = 0
}
$form1_FormClosing = [System.Windows.Forms.FormClosingEventHandler]{
#Event Argument: $_ = [System.Windows.Forms.FormClosingEventArgs]
Write-Host Form closing
}
$form1_FormClosed = [System.Windows.Forms.FormClosedEventHandler]{
#Event Argument: $_ = [System.Windows.Forms.FormClosedEventArgs]
Write-Host Form Closed
}
$form1_ParentChanged = {
Write-Host Parent
}
$buttonRunProcess_Click = {
#TODO: Place custom script here
Run-Process -count $script:count -sync $form1
}
$buttonSendInput_Click = {
#TODO: Place custom script here
$p.StandardInput.WriteLine($textboxInput.Text)
$p.StandardInput.WriteLine("`n") # simulate 'ENTER'
}