user13657
user13657

Reputation: 765

Show progressBar until window.show()

I have problem with showing progress bar while window is loading. Actually i have window with a lot of items in datagrid. When im calling window.Show(), it tooks very long time till its open, so im wondering, if its possible to call something like:

 ShowProgressBar spb = new ShowProgressBar();
            spb.Topmost = true;
            spb.Owner = this.Owner;
            spb.Show();

            while(mainWin.isLoaded)
                  spb.updatePB(); // this method updating progressbar.value.
mainWindow.Show();

But it doesnt show progresbarr at all, while loading, only show when window is full-loaded.

Is there any helpful code? ;)

Upvotes: 0

Views: 2542

Answers (2)

Blachshma
Blachshma

Reputation: 17385

Your problem is that both of them are on the UI thread, so you won't be able to update the UI for the progress bar until you finish loading the MainWindow. The solution is to use another thread to update the ProgressBar's UI....

Something like this should work:

 Dispatcher progressDisptacher;
 var uiThread = new Thread(() =>
  {
      ShowProgressBar spb = new ShowProgressBar();
      spb.Topmost = true;
      spb.Show();
      progressDisptacher = spb.Dispatcher;

      // allowing the main UI thread to proceed 
     System.Windows.Threading.Dispatcher.Run();
   });
   uiThread.SetApartmentState(ApartmentState.STA);
   uiThread.IsBackground = true;
   uiThread.Start();

   mainWindow.Show();
   progressDisptacher.BeginInvokeShutdown(DispatcherPriority.Send);

As you can see, after the mainWindow loads, you can kill the progress bar thread using: progressDisptacher.BeginInvokeShutdown(DispatcherPriority.Send);

Upvotes: 1

Aron
Aron

Reputation: 15772

I assume that you want to update the progress bar when your main window ISN'T loaded. So firstly you should want to invert the while loop.

However its a bit more subtle that single problem.

Welcome to the extremely painful work of STA threads. A quick rule of thumb is that anything that has to do with the what you see on the screen must be done with the main thread. And in fact a lot of what happens is when you aren't using the main thread, .net uses it to redraw anything that has changed (like the Progress bar).

To be able to show the progress bar you are going to have to return control of the UI thread back to what is called the message loop. The easiest way to do so is to return the method call. But before that you will want to setup a timer to periodically check the progress.

Your current code would just spend all day checking if the mainWindow is loaded, and not actually loading the mainWindow.

However the actual loading of the mainWindow is likely going to again need to use the main thread to construct.

Soooo...finally you should IsAsync out the binding that loads the items into the datagrid.

Upvotes: 0

Related Questions