gpt4 book ai didi

winforms - 使用Windows窗体在脚本终止后数分钟内锁定PowerShell ISE

转载 作者:行者123 更新时间:2023-12-03 13:01:55 35 4
gpt4 key购买 nike

我在这里有一个有趣的问题。我正在创建一个日历选择器,以便在创建帐户时使用。它可以正常工作,并且仍在进行中,但是我注意到,当我在Powershell ISE中运行脚本时,几分钟后它将锁定(在此之前,我可以编辑和保存代码几分钟)。事件日志中没有任何内容。我收到一个对话框,说Powershell没有响应。内存使用情况似乎也很正常。我不知道发生了什么。

无论我如何运行Powershell ISE(以管理员身份运行,以另一个帐户运行,以及以普通ISE运行),我都会运行Windows 8.1。

一位同事建议这可能是公寓模型,因此我尝试了STA和MTA,但是无论哪种方式都会出现问题。从控制台主机运行相同的代码时,不会发生这种情况。

[void] [System.Reflection.Assembly]::LoadWithPartialName("System.Windows.Forms")
[void] [System.Reflection.Assembly]::LoadWithPartialName("System.Drawing")

$objForm = New-Object Windows.Forms.Form

$objForm.Text = "Select a Date"
$objForm.Size = New-Object Drawing.Size @(490,250)
$objForm.StartPosition = "CenterScreen"

$objForm.KeyPreview = $True

$objForm.Add_KeyDown({
if ($_.KeyCode -eq "Enter")
{
$script:dtmDate=$objCalendar.SelectionStart
$objForm.Close()
}
})

$objForm.Add_KeyDown({
if ($_.KeyCode -eq "Escape")
{
$objForm.Close()
}
})

$objCalendar = New-Object System.Windows.Forms.MonthCalendar
$objCalendar.Text = "Start"
$objCalendar.ShowTodayCircle = $False
$objCalendar.MaxSelectionCount = 1
$objForm.Controls.Add($objCalendar)

$objForm.Topmost = $True

$objForm.Add_Shown({$objForm.Activate()})
[void] $objForm.ShowDialog()

if ($dtmDate)
{
Write-Host "Date selected: $dtmDate"
}

$objForm.Dispose()

回应@The Unique Paul Smith

function Find-CalenderDateTest {
[CmdletBinding()]
param(
[Parameter(
Mandatory=$false
)]
[ValidateSet('long','short','powerpoint')]
[ValidateNotNullOrEmpty()]
[string]
$DateFormat

)

Begin{
[void] [System.Reflection.Assembly]::LoadWithPartialName("System.Windows.Forms")
[void] [System.Reflection.Assembly]::LoadWithPartialName("System.Drawing")

$objForm = New-Object Windows.Forms.Form

$objForm.Text = "Select a Date"
$objForm.Size = New-Object Drawing.Size @(243,250)
$objForm.StartPosition = "CenterScreen"

$objForm.KeyPreview = $True

$dtmDate = $null

$objForm.Add_KeyDown( {
if ($_.KeyCode -eq "Enter")
{
$dtmDate=$objCalendar.SelectionStart
$objForm.Close()
}
})


$objForm.Add_KeyDown({
if ($_.KeyCode -eq "Escape")
{
$objForm.Close()
}
})

#region OK Button
$OKButton = New-Object System.Windows.Forms.Button
$OKButton.Location = New-Object System.Drawing.Size(20,175)
$OKButton.Size = New-Object System.Drawing.Size(75,23)
$OKButton.Text = "OK"

# Got rid of the Click event for OK Button, and instead just assigned its DialogResult property to OK.
$OKButton.DialogResult = [System.Windows.Forms.DialogResult]::OK

$objForm.Controls.Add($OKButton)

# Setting the form's AcceptButton property causes it to automatically intercept the Enter keystroke and
# treat it as clicking the OK button (without having to write your own KeyDown events).
$objForm.AcceptButton = $OKButton
#endregion

#region Cancel Button
$CancelButton = New-Object System.Windows.Forms.Button
$CancelButton.Location = New-Object System.Drawing.Size(80,175)
$CancelButton.Size = New-Object System.Drawing.Size(75,23)
$CancelButton.Text = "Cancel"

# Got rid of the Click event for Cancel Button, and instead just assigned its DialogResult property to Cancel.
$CancelButton.DialogResult = [System.Windows.Forms.DialogResult]::Cancel

$objForm.Controls.Add($CancelButton)

# Setting the form's CancelButton property causes it to automatically intercept the Escape keystroke and
# treat it as clicking the OK button (without having to write your own KeyDown events).
$objForm.CancelButton = $CancelButton
#endregion

$objCalendar = New-Object System.Windows.Forms.MonthCalendar
$objCalendar.ShowTodayCircle = $False
$objCalendar.MaxSelectionCount = 1
$objForm.Controls.Add($objCalendar)

$objForm.Topmost = $True

$objForm.Add_Shown({$objForm.Activate()})

$Results = $objForm.ShowDialog()
}

Process{}

End{
if ($Results -eq "OK")
{
$objCalendar.SelectionStart
}

$objForm.Dispose()

}
}

最佳答案

错误是MTA / STA

不要使用

$form.showDialog()

使用
[system.windows.forms.application]::run($form)

代替

而且每次都能正常工作

另一种方法是将其放在另一个线程中:
$code
{
//form code here
$form.showDialog()
}
$newThread = [Powershell]::Create()
$newThread.AddScript($code)
$handle = $newThread.BeginInvoke()

提供调用脚本中的变量:
$newThread.Runspace.SessionStateProxy.SetVariable("variablenname",value)

BeginInvoke之前使用不带$ ...的 variablenname

关于winforms - 使用Windows窗体在脚本终止后数分钟内锁定PowerShell ISE,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30808084/

35 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com