Results 1 to 6 of 6

Thread: Background Worker Progress

  1. #1

    Thread Starter
    Fanatic Member clarkgriswald's Avatar
    Join Date
    Feb 2000
    Location
    USA
    Posts
    751

    Background Worker Progress

    I have background worker that performs several operations. In the DoWork event, I call the ReportProgress method before each operation, to update a status modal that is displayed to the user (in the ProgressChanged event). Some of the operations are so quick, that the status never gets a chance to update. I would like to ensure the user sees each status step for at least say, 500ms before moving to the next operation.

    I tried starting a timer in the ProgressChanged event (interval of 500) and trying to wait there, but the ProgressChanged event doesn't seem to fire before the next operation is already underway:

    VB Code:
    1. Private Sub Worker_ProgressChanged(sender As Object, e As ProgressChangedEventArgs) Handles Worker.ProgressChanged
    2.  
    3.         WaitForStatusTimerToFinish()
    4.  
    5.         StatusLabel.Text = CStr(e.UserState)
    6.         Refresh()
    7.  
    8.         StatusTimer.Start()
    9.  
    10.     End Sub
    11.  
    12.     Private Sub WaitForStatusTimerToFinish()
    13.         Do While StatusTimer.Enabled
    14.             StatusLabel.Refresh()
    15.             Application.DoEvents()
    16.         Loop
    17.     End Sub

    So, let's say I have 5 operations, Step 1-5.

    I want the user to see each step:
    Step 1...
    Step 2...
    Step 3...
    Step 4...
    Step 5...

    Right now, I may only see the following due to the speed of operation 2 and 5:
    Step 1...
    Step 3...
    Step 4...

    Any thoughts on how to accomplish this?
    Last edited by clarkgriswald; Dec 6th, 2022 at 09:26 AM.

  2. #2
    Smooth Moperator techgnome's Avatar
    Join Date
    May 2002
    Posts
    34,064

    Re: Background Worker Progress

    1) This doesn't do what you think it does... the opposite actually.
    Code:
        Private Sub WaitForStatusTimerToFinish()
            Do While StatusTimer.Enabled
                StatusLabel.Refresh()
                Application.DoEvents()
            Loop
        End Sub
    2) It's also a form of a busy wait... which is never a good idea.

    3) Honestly, just let the display update as fast as it can... most users aren't interested in each individual status message anyhow. They just want to know when the overall operation is complete.

    4) On that note, if your statuses update faster than the user can see, they'll think your system is fast. You start putting in needless delays, then is slows down the system and users for the most part don't like that. They're an impatient lot.

    -tg
    * I don't respond to private (PM) requests for help. It's not conducive to the general learning of others.*
    * I also don't respond to friend requests. Save a few bits and don't bother. I'll just end up rejecting anyways.*
    * How to get EFFECTIVE help: The Hitchhiker's Guide to Getting Help at VBF - Removing eels from your hovercraft *
    * How to Use Parameters * Create Disconnected ADO Recordset Clones * Set your VB6 ActiveX Compatibility * Get rid of those pesky VB Line Numbers * I swear I saved my data, where'd it run off to??? *

  3. #3
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    37,844

    Re: Background Worker Progress

    I agree with the conclusions that TG came to. What I was going to say is that some processes will be too fast to give the user meaningful feedback. In those cases, if you MUST give them feedback, then you're going to have to implement a delay, which should be in the background process, thereby delaying raising the ProgressChanged event. However, TG is more right than that answer, because introducing an artificial delay just so the user can see a message, is almost always going to be a bad idea. They aren't going to thank you, usually.
    My usual boring signature: Nothing

  4. #4
    .NUT jmcilhinney's Avatar
    Join Date
    May 2005
    Location
    Sydney, Australia
    Posts
    109,263

    Re: Background Worker Progress

    I don't disagree with what has already been said but I have an idea for you if you're determined to have the user see every message. Don't use ReportProgress and ProgressChanged. Instead, use a ConcurrentQueue to store the messages. In the DoWork event handler, just add messages to the queue when appropriate. Use a Timer with an Interval of 500 and, in the Tick event handler, try to dequeue an item and, if you succeed, display that item.

  5. #5

    Thread Starter
    Fanatic Member clarkgriswald's Avatar
    Join Date
    Feb 2000
    Location
    USA
    Posts
    751

    Re: Background Worker Progress

    Thanks for all the input guys. To clarify why I had wanted the user to "see" the messages...the operations are part of a check for updates process (I have consolidated some steps):
    Step 1: checking for updates
    Step 2: new version detected
    Step 3: installing new version

    When running, step 3 is not displayed because it kicks the process off and closes down the main app too quickly. So they would see new version detected, and then maybe a 5-6 seconds of nothing before the new version opened. I wanted them to see the "installing new version" before it shutdown.

  6. #6
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    37,844

    Re: Background Worker Progress

    Well, I'd say you're right. Giving them nothing to look at for that long is sure to cause you headaches. Some people will just assume it isn't working.

    It sounds like the old version goes away completely, such that the user is left looking at their desktop, before the new version comes up. I'd say the ideal would be to put up some kind of fašade screen, like a splash screen, during that time. You may not be able to do that, though, in which case I'd be inclined to raise the Report Progress event to put up some information about a new version being installed, and that it will take a few seconds, and then wait in the background worker. The UI thread doesn't need to wait, just the background worker needs to pause for a few seconds to let the user digest the information before kicking off the next step of the process.

    So, the background process would do this:
    1) If a new version is needed, raise Report Progress.
    2) Wait for some modest amount of time.
    3) Go on with the new install.
    My usual boring signature: Nothing

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width