views:

780

answers:

5

I don't want the user to interact with my application while a certain backgroundworker is busy (working). I created this bgw so that the application doesn't look frozen when it's working. But now users can move around in the app. How do I disable my form/application?

Thanks!

+4  A: 

Perhaps set Enabled to false?

this.Enabled = false;

That is a bit drastic though, since it also prevents the form from being moved, resized or event closed. A better approach would be to put a Panel control in your form, that has Dock = Fill, and put our other controls into that Panel. Then you can instead use the Enabled property of the Panel to prevent further user input.

Note thought that the user will be able to close the form, so that should be handled gracefully in some way.

Fredrik Mörk
This is a quick and dirty way to do it, but it could be better (depending on your situation) than disabling every control on the form that the user can interact with.
Michael Todd
@Michael: disabling the Form is indeed quick and dirty :o)
Fredrik Mörk
Thanks, I did something similar to what Michael suggested.
Chris
And also what Fredrik supplemented to his original answer... Thanks!
Chris
A: 

Another possible way could be that you "filter out" all the input to the application. This could be done by listening to the "KeyDown" and "MouseButtonDown". Once the background job is triggered you could set the FILTER_INPUT flag to true and reset it once done. If the FILTER_INPUT flag is set then could cancel all the Key and Mouse events.

This may not be the most efficient since all KeyPress and Clicks are going to go thro the Filter check.

Codex
+1  A: 

I agree with @michael-todd in his comment above, disabling individual controls/navigation buttons/etc. while the background worker is working seems like a fairly good solution. This would give you fine-grained control over what the user can do during the specific background operation.

You could:

  1. Create methods to enable or disable all appropriate navigation/interaction controls (by setting their Enabled property to true/false, etc. as appropriate for each control)
  2. Call the "Disable" method from your code right before you call StartWorkerAsync() on your background worker
  3. In the event handler for RunWorkerCompleted, call the "Enable" method to re-enable the view for user input
Guy Starbuck
+3  A: 

You could also create a modal "busy splash" dialog that is shown when the background task starts and removed programmatically when the task ends. You could put a little animation in that box too to let the users know that something is going on. You would also need to make sure they don't close the dialog manually (only allow it to be closed programmatically).

Garo Yeriazarian
This can be quite a good trick, especially when you want the Main Form to remain visible and unchanged. You could even use a very small or hidden DialogForm.
Henk Holterman
The other thing I've done is to have everything in the form contained in a panel, then hide the panel and put a "Busy" message up. This way there's no way to interact with the underlying controls.
Garo Yeriazarian
A: 

It is easier to manage disabling certain controls by placing them inside a panel and disabling that panel rather than disabling individual controls:

controlPanel.Enabled = false;

A common way to block other tasks, that may meet your needs, is by showing a top most form with a progress bar. I've implemented this in the past with success. Other programs do the same thing. For example, in WinRAR, when the applciation is busy extracting or compressing files, the application shows a top most form. It looks like a "modal" form, but in fact, you can still click on the other functions, to which WinRAR asks, "Do you wish to abort the current operation?"

Disabling the entire application is often not necessary and may not be intuitive. So, ask yourself if you really need to block interaction with the form. For example, I have an application that takes some time to complete certain tasks. I provide a progress bar indicator for that particular piece of work, but you can still interact with the application to start additional tasks that run simultaneously. Even if I only allowed you to perform a single task at a time, you still may want to view the help file or set application preferences while the task was running. In addition, I give the user a button that allows them to stop the task. Disabling the form would prevent this type of interaction.

Marcus Adams