Search code examples
c#.netwpfmultithreadingbackgroundworker

Instantiating an object in a background worker causes the UI to freeze up


This is what i have at the moment, but when i call Dispatcher.BeginInvoke(), my UI freezes up:

        BackgroundWorker backgroundWorker = new BackgroundWorker();
        backgroundWorker.WorkerSupportsCancellation = true;
        backgroundWorker.WorkerReportsProgress = true;


        ViewModel.GenerateReport(backgroundWorker, Dispatcher);

ViewModel:

backgroundWorker.DoWork += delegate(object s, DoWorkEventArgs args)
        {
            try
            {
                ReportViewModel reportViewModel = new ReportViewModel(SessionContext, Mediator, reportDashboardViewModel.ReportRequest, false);

                dispatcher.BeginInvoke((Action)(() =>
                {
                    ReportPreviewView reportPreviewView = new ReportPreviewView(reportViewModel);
                    reportPreviewView.ReportName = reportDashboardViewModel.ReportRequest.Report.ReportName;

                    ReportView = reportPreviewView;
                }));
            }
            catch (Exception exception)
            {
                backgroundWorker.ReportProgress(0, "There Was an Error generating the report");
                backgroundWorker.CancelAsync();
                throw;
            }
        };

        backgroundWorker.RunWorkerAsync();

The first line in dispatcher.BeginInvoke causes my UI to freeze up. ReportPreviewView reportPreviewView = new ReportPreviewView(reportViewModel);

Note: ReportPreviewView creates the relevant view for the report request. May it be Devexpress, C1 or pivot reports.

As soon as i remove the dispatcher.BeginInvoke, i get this error:

The calling thread must be STA, because many UI components require this.

So my question is, what do i need to do to get around this?

The whole reason for using a BackgroundWorker was so that my UI stays responsive at all times.

I am new to multithreading,so maybe i got the structure all wrong...


Solution

  • Moral of the story, all UI elements needs to be created on the UI thread!

    That being said, if the creation of the UI element takes a long time, the UI will freeze up. Take all the heavy lifting and put it in a Task or BackgroundWorker.

    Then you will have a more responsive UI.