Home | Contact Us | FAQ | Search & Site Map | Link to Us
Sign In | Join | Other 45 Sites in Network
HomeAnnouncementsFree MagazinesWhite PapersSubmit Content
Discussion GroupsASP.NETWindows FormsLanguages.NET FrameworkVisual Studio.NET
Articles.NET FrameworkASP.NETToolsWindows Forms
.NET DirectoryOpen Source ProjectsUser GroupsWeb Resources
Related Topics
Visual Basic 6SQL ServerMS AccessOther DB ProductsMS Server ProductsMore Topics ...

.NET Forum / Languages / C# / October 2007

Tip: Looking for answers? Try searching our database.

Fire event in the same thread as the UI like BackgroundWorker

Thread view: 
Enable EMail Alerts  Start New Thread
Thread rating: 
Sin Jeong-hun - 21 Oct 2007 18:26 GMT
This is what I've always been wondered.
Suppose I've created a class named Agent, and the Agent does some
lengthy job. Of course I don't want to block the main window, so the
Agent does the job in a separate thread. If the job is progressed it
fires an event, and the main window handled the event by changing the
value of a progress bar. The problem is that this event is fired in
another thread so when the handler in the main window tries to access
the progress bar, an exception occurs. Until now, I've been solving
this problem by checking InvokeRequired and creating a delegate.

But the .NET 2.0's built-in BackgroundWorker seems to have solved this
with a very elegant way. When a BackgroundWorker fires the progress
event, it looks like the event is fired in the same thread as the main
window, because the InvalidOperationException does not occur when I
try to access UI controls in the handler. How could this be possible?
I want my Agent class to be able to the same thing. Making a lot of
delegations in the main window code makes the code dirty.

Please give me an idea. Thank you.
Peter Duniho - 21 Oct 2007 18:46 GMT
> [...]
> But the .NET 2.0's built-in BackgroundWorker seems to have solved this
[quoted text clipped - 6 lines]
>
> Please give me an idea. Thank you.

I don't know the specifics of how BackgroundWorker does it.  Since it
doesn't require a specific Control instance given to it, I suspect it's
using AsyncOperation or something similar.

I'm pretty sure it raises events on the same thread that created the
BackgroundWorker when possible (though, if I recall correctly that's not
actually what it does in a console application...it does depend on
having a message pump), not specifically the main UI thread.

You could either use AsyncOperation yourself (you'd initialize it when
your object is created, and then use it to raise events on the same
thread used to create the object).  Alternatively, if your object
depends on a specific Control instance, you may find it easier to just
use the Control instance to invoke a method to raise the event.

Pete
Peter Ritchie [C# MVP] - 22 Oct 2007 15:53 GMT
Yes, BackgroundWorker uses AsyncOperation to marshal the call back to the
correct thread.  It doesn't use a particular control thread, it simply uses
the thread that was used to create the BackgroundWorker object.

Signature

Browse http://connect.microsoft.com/VisualStudio/feedback/ and vote.
http://www.peterRitchie.com/blog/
Microsoft MVP, Visual Developer - Visual C#

> > [...]
> > But the .NET 2.0's built-in BackgroundWorker seems to have solved this
[quoted text clipped - 23 lines]
>
> Pete
kentcb@internode.on.net - 22 Oct 2007 17:00 GMT
Interesting. I hadn't seen the AsyncOperation class before. It's worth
noting that it is just a wrapper for the SynchronizationContext class
though. It is the particular current SynchronizationContext (available
via SynchronizationContext.Current) that does the actual work of
marshalling to the correct thread. If you're running Winforms, it'll
be a WindowsFormsSynchronizationContext. For WPF, it'll be a
DispatcherSynchronizationContext.

So AsyncOperation makes it easier to post progress and completion of
an operation to the UI (or "contextual") thread. Cool stuff.

Kent
Sin Jeong-hun - 25 Oct 2007 16:58 GMT
On Oct 23, 1:00 am, "ken...@internode.on.net"
<ken...@internode.on.net> wrote:
> Interesting. I hadn't seen the AsyncOperation class before. It's worth
> noting that it is just a wrapper for the SynchronizationContext class
[quoted text clipped - 8 lines]
>
> Kent

Right after I posted the original post, I thought maybe disassembling
the BackgroundWorker
would give me a hint. So I did it. It used several classes I'd never
seen before, and the logic
was quite unfamilar to me. But after all, I modified my class
according to the way BackgroundWoker
works, and now it works just like the BackgroundWorker. I don't need
to use InvokeRequired every time.
I think it would be worth for other people to try this.
Thank you for your replies, all.

Free Magazines

Get these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...

Oracle MagazineNetwork ComputingComputer WorldBio-IT WorldeWeekInformation WeekInfosecurity
 
Sign In
Join
My Latest Posts
My Monitored Threads
My Blog
My Photo Gallery
My Profile
My Homepage

Start New Thread
Enable EMail Alerts
Rate this Thread



©2008 Advenet LLC   Privacy Policy - Terms of Use
This website includes both content owned or controlled by Advenet as well as content owned or controlled by third parties.