views:

223

answers:

3

Hello,

I'd like to have two Threads. Let's call them :

  • Thread A
  • Thread B

Thread A fires an event and thread B listen to this event. When the Thread B Event Listener is executed, it's executed with the Thread A's thread ID, so i guess it is executed within the Thread A.

What I'd like to do is be able to fire event to Thread B saying something like: "hey, a data is ready for you, you can deal with it now". This event must be executed in its own Thread because it uses things that only him can access (like UI controls).

How can I do that ?

Thank you for you help.

A: 

You'll need to marshal the information back into the UI thread.

Typically, you would handle this in your Event handler. For example, say Thread A was your UI thread - when it subscribed to an event on an object in Thread B, the event handler will be run inside Thread B. However, it can then just marshal this back into the UI thread:

// In Thread A (UI) class...
private void myThreadBObject_EventHandler(object sender, EventArgs e)
{
    this.button1.BeginInvoke( new Action(
        () => 
            {
                // Put your "work" here, and it will happen on the UI thread...
            }));
}
Reed Copsey
+3  A: 

The easiest way is probably to subscribe using an event handler which just marshal the "real" handler call onto thread B. For instance, the handler could call Control.BeginInvoke to do some work on thread B:

MethodInvoker realAction = UpdateTextBox;
foo.SomeEvent += (sender, args) => textBox.BeginInvoke(realAction);

...

private void UpdateTextBox()
{
    // Do your real work here
}
Jon Skeet
A: 

If you're using Windows Forms or WPF, and do not have a Control reference handy from your event handlers, you could also capture the reference of System.Threading.SynchronizationContext.Current in something running on the UI thread, and expose that reference to your event handlers.

Then, when you need to have something run on the UI thread, invoke Post() or Send() on the captured SynchronizationContext reference from your event handler, depending on whether you want it to be run asynchronously or synchronously.

Basically this is just sugar around capturing a Control reference and calling Invoke() on it, but can make your code simpler.

Leon Breedt