PowerShell form message displays twice on exit

Ask questions about creating Graphical User Interfaces (GUI) in PowerShell and using WinForms controls.
Forum rules
Do not post any licensing information in this forum.

Any code longer than three lines should be added as code using the 'Select Code' dropdown menu or attached as a file.
User avatar
jroberts671
Posts: 7
Joined: Sun Mar 03, 2013 12:45 pm

PowerShell form message displays twice on exit

Post by jroberts671 » Tue Feb 04, 2020 8:09 am

PowerShell Studio 2020 on Windows 10

Created a simple form that I want to alert the user prior to closing the form.
What I've done is created a menu strip item that has an "Exit". This works as expected. For simplicity I'm just going to use an easy 'OK' message box as shown below.

Code: Select all

$exitToolStripMenuItem_Click={
	[System.Windows.Forms.MessageBox]::Show('Are you sure?', 'Caution!')
			$MainForm.Close()
	}
In order to catch any instance of the user closing the form including if they click the red "X" button I then added a form event for "FormClosing" with the below code,

Code: Select all

$MainForm_FormClosed=[System.Windows.Forms.FormClosedEventHandler]{
#Event Argument: $_ = [System.Windows.Forms.FormClosedEventArgs]
	[System.Windows.Forms.MessageBox]::Show('Are you really sure?', 'Caution!')
			$MainForm.Close()
	}
I added the word "really" to the above message to distinguish which code is producing which messagebox. The above also works as expected, however the issue is now when the user goes to the menu strip "Exit" item, they get the original exit message box and after clicking "OK" they get a second popup for the $Mainform_FormClosed" event.
If I remove the message box from the $Mainform_FormClose and just leave it to $Mainform.Close() then everything works as expected but then I wouldn't need the $Mainform_FormClose event. Also, clicking the red "X" only produces the single message box, so it half works.

I can't figure out why adding the messagebox causes the double popup. I know I could just eliminate the menustrip "Exit" item and force users to use the close red "X" or remove the form controls forcing them to use the menustrip item but I wanted to see if there was a way to leave both, as I find myself using the close red "X" more while others prefer to use the menustrip item.
I've tried different iterations, tried making it a function instead, tried the even "FormClosing" but this just creates a never ending loop.

Any help is greatly appreciated, thanks!

-Jay

User avatar
jroberts671
Posts: 7
Joined: Sun Mar 03, 2013 12:45 pm

Re: PowerShell form message displays twice on exit

Post by jroberts671 » Tue Feb 04, 2020 8:36 am

Just wanted to add that if I include the following into the "Exit" menustrip item, I don't get the double popup message from both events but the form hangs on closing for almost 5 seconds which I know users are going to wonder why the app doesn't seem to be closing or responsive. Here is the code added to the exit menustrip item.
[Environment]::Exit(1)

-Jay

jvierra
Posts: 14155
Joined: Tue May 22, 2007 9:57 am
Contact:

Re: PowerShell form message displays twice on exit

Post by jvierra » Tue Feb 04, 2020 12:31 pm

Place the message code in the "FormClosing" event and not the "FormClosed" event.

User avatar
jroberts671
Posts: 7
Joined: Sun Mar 03, 2013 12:45 pm

Re: PowerShell form message displays twice on exit

Post by jroberts671 » Tue Feb 04, 2020 8:49 pm

I tried the code in the $form1_formclosing event as well. This still produces two message boxes, the first from the menustrip event as expected, and then a never ending loop one from the form_closing event. It never seems to get to the $form1.close(). I removed the formclosed and added the below

Code: Select all

$exitToolStripMenuItem_Click={
	[System.Windows.Forms.MessageBox]::Show('Are you sure?', 'Caution!')
	$form1.Close()
}

$form1_FormClosing=[System.Windows.Forms.FormClosingEventHandler]{
#Event Argument: $_ = [System.Windows.Forms.FormClosingEventArgs]
	#TODO: Place custom script here
	[System.Windows.Forms.MessageBox]::Show('Are you really sure?', 'Caution!')
	$form1.Close()
}
-Jay

User avatar
jroberts671
Posts: 7
Joined: Sun Mar 03, 2013 12:45 pm

Re: PowerShell form message displays twice on exit

Post by jroberts671 » Tue Feb 04, 2020 9:02 pm

Sometimes you just have to walk away for a bit.
I went back to the original FormClosed event but added the .add_FormClosed into the code for the below.

Code: Select all

$form1_FormClosed=[System.Windows.Forms.FormClosedEventHandler]{
#Event Argument: $_ = [System.Windows.Forms.FormClosedEventArgs]
	#TODO: Place custom script here
	$form1.add_FormClosed({
			[System.Windows.Forms.MessageBox]::Show('Are you really sure?', 'Caution!')
			
			$form1.Close()
		})
}
Now when the user clicks the "Exit" menu from the menustrip, they are presented with one message box and when they click OK the form closes as expected. Same thing when they click the "X" close button on the form, they are only presented with the single message box.
Thanks!

-Jay

jvierra
Posts: 14155
Joined: Tue May 22, 2007 9:57 am
Contact:

Re: PowerShell form message displays twice on exit

Post by jvierra » Tue Feb 04, 2020 9:25 pm

I have no issues like that. You are likely coding this in a way that causes the closing event to be canceled. Without an example of code that does this there is no way to know how you got into this loop.

Also you cannot call form.Close() from a closed or closing event. Just close the form once in one place usually in a button. The rest is automatic.

jvierra
Posts: 14155
Joined: Tue May 22, 2007 9:57 am
Contact:

Re: PowerShell form message displays twice on exit

Post by jvierra » Tue Feb 04, 2020 9:29 pm

jroberts671 wrote:
Tue Feb 04, 2020 9:02 pm
Sometimes you just have to walk away for a bit.
I went back to the original FormClosed event but added the .add_FormClosed into the code for the below.

Code: Select all

$form1_FormClosed=[System.Windows.Forms.FormClosedEventHandler]{
#Event Argument: $_ = [System.Windows.Forms.FormClosedEventArgs]
	#TODO: Place custom script here
	$form1.add_FormClosed({
			[System.Windows.Forms.MessageBox]::Show('Are you really sure?', 'Caution!')
			
			$form1.Close()
		})
}
Now when the user clicks the "Exit" menu from the menustrip, they are presented with one message box and when they click OK the form closes as expected. Same thing when they click the "X" close button on the form, they are only presented with the single message box.
Thanks!

-Jay
No. That is not how to code anything. Adding the event to the event again in the event handler will not do anything useful.

User avatar
jroberts671
Posts: 7
Joined: Sun Mar 03, 2013 12:45 pm

Re: PowerShell form message displays twice on exit

Post by jroberts671 » Thu Feb 06, 2020 6:37 am

If you have a better idea I'm listening.
When I added the full code I am noticing it is still going through both close events it's just doing it very fast but you can still see it in the background so I'm back to square one.
It's easy enough to reproduce and you don't need to use a menustrip item, I was able to reproduce using a simple button.

New form, single button and a closed event, add a message box to both and have both close the form and when you use the button it will repeat the message box from the closed event, or closing event, or close event. Any of those will produce the same behavior.

-Jay

User avatar
jroberts671
Posts: 7
Joined: Sun Mar 03, 2013 12:45 pm

Re: PowerShell form message displays twice on exit

Post by jroberts671 » Thu Feb 06, 2020 6:43 am

Here is the PSF
Track.psf
(20.6 KiB) Downloaded 5 times

User avatar
jroberts671
Posts: 7
Joined: Sun Mar 03, 2013 12:45 pm

Re: PowerShell form message displays twice on exit

Post by jroberts671 » Thu Feb 06, 2020 9:31 am

I think I might have it with the code below. Not sure if this is the best way or not but it does work as expected now. It's now loaded into a function for ease.

Code: Select all

$form1_Load={
	#TODO: Initialize Form Controls here
	
}
function close
{
	$resultmain = [System.Windows.Forms.MessageBox]::Show('Do you want to save your session before exiting?', 'Caution!', 'YesNo', 'Warning')
	Try
	{
		if ($resultmain -eq 'Yes')
		{
			[void][System.Windows.Forms.CloseReason]::UserClosing
			[void][System.Windows.Forms.Application]::ExitThread()			
		}
		else
		{
			[void][System.Windows.Forms.Application]::ExitThread()
			[void][System.Windows.Forms.CloseReason]::UserClosing
			return
		}
	}
	catch
	{

	}
}

$form1_FormClosed=[System.Windows.Forms.FormClosedEventHandler]{
#Event Argument: $_ = [System.Windows.Forms.FormClosedEventArgs]
	#TODO: Place custom script here
close
}

$button1_Click={
	#TODO: Place custom script here
	close
}
And below is the PSF file if anyone is interested.
Track.psf
(20.86 KiB) Downloaded 4 times

Post Reply