Question

I have two non UI Threads.

  • Thread A
  • Thread B

Thread A raise an event and Thread B listen to this event. When the Thread B Event Listener is executed, it got executed on Thread A (I think, because Thread A raises the event).

What I'd like to do is, be able to raise an event on Thread A and if Thread B is listening, the Listener should get executed on Thread B.

Something like this:

    private void SomeMethodOnThreadA()
    {
        synchronizationContextOfThreadB.Send(new SendOrPostCallback(o =>
                    {
                        EventXy(this, new EventArgs());
                    }), null);
    }

But this is not working since I’m my threads are non UI threads.

Was it helpful?

Solution

Thread B isn't listening to the event. It may have been the thread that added the event handler, but that thread isn't what's listening.

You can't just go at any time and tell a currently running thread to go and execute some other method instead of what it's doing. When you start a new thread you give it a place to start, and it just executes code there until it's done, and that's all.

When you run code on the UI thread you can do it because the UI thread has a message loop. It has a queue of delegates, and the code that the thread is running looks something like this:

while(!applicationStopped)
{
    Action nextAction = queue.Dequeue();
    nextAction();
}

While there is a bit more to it (error handling, for example) that's the general idea. To "run code in the UI thread" you just add a delegate to the queue, and it will eventually be run in the UI thread.

You'll need some similar mechanism if you want to run code in your thread B. You'll need to have some sort of delegate, queue, or other medium of providing a delegate that it should execute, and that thread needs to be checking that location for delegates that it's supposed to run. In the general case, this is often not feasible, unless this other thread is similar to a UI thread in that it does nothing but execute delegates it's given from other locations.

OTHER TIPS

A Thread isn't responsible for receiving an event. It's the thread that invokes the eventhandlers.

You can go two ways:

1) Using something like a messaging queue. Thread A queue's an object to a queue (dataobject/action) and thread B tries to process items from the queue. (Fire and Forget) So Thread B must monitor the queue.

2) You could create a dispatcher on that thread and Invoke an Action on it. (I made a simple DispatcherThread class here: http://csharp.vanlangen.biz/threading/dispatcherthread/) it will create a thread with a Dispatcher so you can invoke actions on it.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top