Progresschanged not updating backgroundworker glad

Tuesday, September 26, 2017 by Finn

using System;
using System.ComponentModel;
using System.Windows.Forms;

namespace BackgroundWorkerExample
    public partial class Form1 : Form
        private BackgroundWorker bw;

        public Form1()

   = new BackgroundWorker();
   += new DoWorkEventHandler(bw_DoWork);
   += new ProgressChangedEventHandler(bw_ProgressChanged);
   += new RunWorkerCompletedEventHandler(bw_RunWorkerCompleted);
   = true;
            this.button1.Click += new EventHandler(button1_Click);

        private void button1_Click(object sender, EventArgs e)
            if (!
                this.button1.Enabled = false;

        private void bw_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
            this.label1.Text = "The answer is: " + e.Result.ToString();
            this.button1.Enabled = true;

        private void bw_ProgressChanged(object sender, ProgressChangedEventArgs e)
            this.label1.Text = e.ProgressPercentage.ToString() + "% complete";

        private void bw_DoWork(object sender, DoWorkEventArgs e)
            BackgroundWorker worker = (BackgroundWorker)sender;
            for (int i = 0; i < 100; ++i)
                // report your progres

                // pretend like this a really complex calculation going on eating up CPU time
            e.Result = "42";

The DoWork Event

The handler you add to this event will be run in a separate thread. The event args (DoWorkEventArgs) has two properties that are used to pass parameters to the background thread and send results back to the main thread.

  • Argument - an object. This is the argument you pass in when you start the work. I'll show you how to use this later.
  • Result - an object. When you finish the work, you want to set this to the result you calculated.

The RunWorkerCompleted Event

When the background worker finishes its work, this event will be fired in the original thread. The RunWorkerEventArgs also has a property called Result which is set to the value you set Result to in the DoWorkEventArgs in the DoWork handler mentioned above.

The ProgressedChanged Event

"Please wait..." isn't exciting at all. Up-to-the-second feedback can be created with the ProgressChanged event. The sender object of the DoWork event is the background worker itself. When you call ReportProgress in the DoWork handler, the ProgressChanged event is fired in the main thread. The ProgressChangedEventArgs has a property called ProgressPercentage, being the value you passed in to ReportProgress.

RunWorkerAsynch Method

This is how the DoWork event gets kicked off. RunWorkerAsynch, as you can probably guess, does not block the current thread's execution. It'll make the BackgroundWorker fire the DoWork event in a new thread, however, it's best to check the IsBusy property otherwise you'll get a crash if the worker as already been started. This could happen if, for example, you took out the code to disable the button above. Additionally, you can also pass an object into the RunWorkerAsynch method and it will appear in the DoWorkEventArgs as the Argument property mentioned above.

So now you have absolutely no excuse to block a UI thread in .NET.