PowerShell GUI输出

时间:2013-09-20 07:07:27

标签: powershell user-interface ping

我正在编写一个带有GUI的小型PowerShell脚本,用于处理Ping命令。目前我有来自用户的脚本读取输入,以确定要ping的IP地址/ URL,然后将输出显示到富文本框。

但是,目前,命令COMPLETES会立即写入整个输出。我希望它能实时显示每一行输出 - 这样它的外观与在shell中运行命令的方式相同。

按下Ping按钮时,会调用以下函数(我认为这就是问题所在):

Function FNPing {
    $OutputBox.Text = "Please Wait..."
    $ping = ping ($InputBox.text)
    $OutputBox.Text = ""
    foreach ($line in $ping) {
        $OutputBox.Appendtext($line+[char]13+[char]10)
    }
}

我想这个问题可能在ForEach声明中得到解决,我只是不知道该怎么做!感谢所有帮助!

2 个答案:

答案 0 :(得分:2)

我会尝试使用test-connection cmdlet。问题是ping一个外部exe,所以当你完成时,你所有的东西都是一团文字。在运行时获取ping输出的唯一方法是使用start-process并重定向输出(这非常混乱)。

使用test-connection你不会得到一个漂亮的摘要,但信息就在那里。对于摘要信息,measure-object可以提供帮助。这是一个模仿ping的输出,可以让你开始:

function fnping {
    $outputBox.Text = "Please Wait..."
    $count = 4
    $results = test-connection $inputbox.Text -count $count | foreach { $outputBox.AppendText("Reply from $($_.ProtocolAddress): bytes=$($_.ReplySize) time=$($_.ResponseTime)ms TTL=$($_.TimeToLive)`r`n"); $_ }
    $summary = $results | measure-object -Property ResponseTime -Average -Minimum -Maximum
    $lost = $count - $summary.Count
    $percentLost = $lost * 100.0 / $count
    $outputBox.AppendText("Packets: Sent = $count, Received = $($summary.Count), Lost = $lost ($($percentLost)% loss)`r`n")
    $outputBox.AppendText("Minimum = $($summary.Minimum)ms, Maximum = $($summary.Maximum)ms, Average = $($summary.Average)ms`r`n")
}

修改

其实我站得更正了。将结果分配给变量($ping)会导致powershell等待输出流关闭。您可以使用foreach-object轻松完成所需操作。在这里我使用一个小辅助函数来清除输出框,然后写入框:

function WriteEach-Object() { 
    param(
      [Parameter(Mandatory=$true,ValueFromPipeline=$true)]
      [object[]]$inputs
    )  

    begin { $outputBox.Text = "" } 
    process { $inputs | foreach { $outputBox.AppendText($_) } } 
    end { $outputBox.AppendText("`r`n") } 
}

function fnping() {
    $outputBox.Text = "Please Wait..."
    ping $inputBox.Text | writeeach-object
}

答案 1 :(得分:0)

您需要添加BEGIN {} PROCESS {}和END {}语句来控制函数的工作方式。如果没有给出这样的话,Powershell会假设所有内容都在END {}语句中,一次处理所有内容。

改为

Function FNPing {
  BEGIN {
  }

  PROCESS {
     $OutputBox.Text = "Please Wait..."
     $ping = ping ($InputBox.text)
     $OutputBox.Text = ""
     foreach ($line in $ping) {
         $OutputBox.Appendtext($line+[char]13+[char]10)
     }
  }

  END {
  }
}

应该做的伎俩。或者,您可以将Function替换为Filter,假设代码位于PROCESS {}块中。

了解更多信息:http://technet.microsoft.com/en-us/magazine/hh413265.aspx