By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
434,870 Members | 2,347 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 434,870 IT Pros & Developers. It's quick & easy.

Asynchronous Event Raising

P: n/a
Hi all,
How Can You Raise Events Asynchronously ?
Now for the details ...

I want to do inter modular communication using events in such a way that the
contributing modules need not maintain the reference to any module.

For e.g. There is one EventManager class that has event declaration and
public functions that raise events. So any other class that needs to publish
data to interested classes, can call the event raiser method of the
EventManager class. The interested classes would already by handling the
event and will get the notification/data.

Public Class EventManager

Public Shared Event m_Notification()

Public Shared Sub NotificationRaiser()

RaiseEvent m_Notification()

End Sub

End Class
Thats fine and working. Now the problem is that the Event raising mechanism
in .NET is synchronous so in above example the control wont leave the
NotificationRaiser until all classes that handle the notification have done
their task. I would like this to be on separate thread (as much
automatically as possible - dont wanna do the plumbing myself).

So is there any way to raise some event asynchronously (like on some other
thread) without the reference of the class that is handling the event.

I hope I made myself clear, if there are still any queries .. then plz lemme
know.

Any suggestion or reference is welcome.

Thanx
rawCoder
Nov 21 '05 #1
Share this Question
Share on Google+
4 Replies


P: n/a
Just to make myself a lil more clear ....
Want it like it was in Win32 PostMessage ...
Fire And Forget ...
"rawCoder" <ra******@hotmail.com> wrote in message
news:uT**************@tk2msftngp13.phx.gbl...
Hi all,
How Can You Raise Events Asynchronously ?
Now for the details ...

I want to do inter modular communication using events in such a way that the contributing modules need not maintain the reference to any module.

For e.g. There is one EventManager class that has event declaration and
public functions that raise events. So any other class that needs to publish data to interested classes, can call the event raiser method of the
EventManager class. The interested classes would already by handling the
event and will get the notification/data.

Public Class EventManager

Public Shared Event m_Notification()

Public Shared Sub NotificationRaiser()

RaiseEvent m_Notification()

End Sub

End Class
Thats fine and working. Now the problem is that the Event raising mechanism in .NET is synchronous so in above example the control wont leave the
NotificationRaiser until all classes that handle the notification have done their task. I would like this to be on separate thread (as much
automatically as possible - dont wanna do the plumbing myself).

So is there any way to raise some event asynchronously (like on some other
thread) without the reference of the class that is handling the event.

I hope I made myself clear, if there are still any queries .. then plz lemme know.

Any suggestion or reference is welcome.

Thanx
rawCoder

Nov 21 '05 #2

P: n/a
rawCoder,

If you have a reference to a delegate list (which is what your event is
declared at, ultimately), then all you have to do is call the BeginInvoke
method, and it will be fired on another thread. However, the event handlers
have to code against the fact that the event notification will be on another
thread.

Hope this helps.
--
- Nicholas Paldino [.NET/C# MVP]
- mv*@spam.guard.caspershouse.com

"rawCoder" <ra******@hotmail.com> wrote in message
news:uT**************@tk2msftngp13.phx.gbl...
Hi all,
How Can You Raise Events Asynchronously ?
Now for the details ...

I want to do inter modular communication using events in such a way that
the
contributing modules need not maintain the reference to any module.

For e.g. There is one EventManager class that has event declaration and
public functions that raise events. So any other class that needs to
publish
data to interested classes, can call the event raiser method of the
EventManager class. The interested classes would already by handling the
event and will get the notification/data.

Public Class EventManager

Public Shared Event m_Notification()

Public Shared Sub NotificationRaiser()

RaiseEvent m_Notification()

End Sub

End Class
Thats fine and working. Now the problem is that the Event raising
mechanism
in .NET is synchronous so in above example the control wont leave the
NotificationRaiser until all classes that handle the notification have
done
their task. I would like this to be on separate thread (as much
automatically as possible - dont wanna do the plumbing myself).

So is there any way to raise some event asynchronously (like on some other
thread) without the reference of the class that is handling the event.

I hope I made myself clear, if there are still any queries .. then plz
lemme
know.

Any suggestion or reference is welcome.

Thanx
rawCoder

Nov 21 '05 #3

P: n/a
BeginInvoke won't work directly because it can only be called on a
delegate with a single subscriber and will throw an exception if you
have multiple subscribers.

Also if you use BeginInvoke you must call EndInvoke.

Take a look at the following AsyncHelper Class.

The AsyncHelper.FireAndForget static method allows you to call a
delegate with a subscriber asynchronously without calling BeginInvoke

The AsyncHelper.FireAsync allows you to call a delegate with multiple
subscribers.

// Based on AsyncHelper by Mike Woodring of
http://staff.develop.com/woodring
//
// Use FireAndForget to execute a method in the thread pool without
having to
// call EndInvoke. Note that the delegate passed to FireAndForget can
only have a
// single Target.
// AsyncHelper.FireAndForget(new MyHandler(MyMethod), methodArg1,
methodArg2, etc);
//
// To Fire an Event asynchronously (with each of the targets being
called on its own thread
// use FireAsync:
// AsyncHelper.FireAsync(MyEvent, eventArg1, eventArg2, ...);
// FireAsync is designed to be called on an event containing zero, one
or more Targets.
// Your FireEvent method does not need to check for null FireAsync will
do it correctly even in a
// multithreaded environment
#region Using Statements
using System;
using System.Reflection;
using System.Threading;
using System.ComponentModel;
#endregion

namespace DanGo.Utilities
{
public class AsyncHelper
{
#region Private Types
// Private class holds data for a delegate to be run on the
thread pool
private class Target
{
#region Private Fields
private readonly Delegate TargetDelegate;
private readonly object[] Args;
#endregion

#region Constructor
/// <summary>
/// Creates a new <see cref="Target"/> instance this holds
arguments and contains
/// the method ExecuteDelegate to be called on the
threadpool.
/// </summary>
/// <param name="d">The users delegate to fire</param>
/// <param name="args">The users arguments to the
delegate</param>
public Target( Delegate d, object[] args)
{
TargetDelegate = d;
Args = args;
}
#endregion

#region Invoker
/// <summary>
/// Executes the delegate by calling DynamicInvoke.
/// </summary>
/// <param name="o">This parameter is required by the
threadpool but is unused.</param>
public void ExecuteDelegate( object o )
{
TargetDelegate.DynamicInvoke(Args);
}
#endregion
}
#endregion

#region Public Static Methods
/// <summary>
/// Fires the delegate without any need to call EndInvoke.
/// </summary>
/// <param name="d">Target Delegate - must contain only one
Target method</param>
/// <param name="args">Users arguments.</param>
public static void FireAndForget( Delegate d, params object[]
args)
{
Target target = new Target(d, args);
ThreadPool.QueueUserWorkItem(new
WaitCallback(target.ExecuteDelegate));
}

/// <summary>
/// Fires each of the members in the delegate asynchronously.
All the members
/// will be fired even if one of them fires an exception
/// </summary>
/// <param name="del">The delegate we want to fire</param>
/// <param name="args">Each of the args we want to
fire.</param>
public static void FireAsync(Delegate del, params object[]
args)
{
// copy the delegate to ensure that we can test for null in
a thread
// safe manner.
Delegate temp = del;
if(temp != null)
{
Delegate[] delegates = temp.GetInvocationList();
foreach(Delegate receiver in delegates)
{
FireAndForget(receiver, args);
}
}
}
#endregion
}
}

Nov 21 '05 #4

P: n/a
Hi raw (or do you prefer Mr Coder?)

It depends on what your observer classes are doing. If they are updating the
screen, for example, you could use BeginInvoke, which will return
immediately.

Otherwise, your observer could start another thread to process the event,
allowing it to return control straight away. Of course, this becomes more
tricky if another notification event is raised before the first one has been
processed, but perhaps then you can afford to wait.

HTH

Charles
"rawCoder" <ra******@hotmail.com> wrote in message
news:uT**************@tk2msftngp13.phx.gbl...
Hi all,
How Can You Raise Events Asynchronously ?
Now for the details ...

I want to do inter modular communication using events in such a way that
the
contributing modules need not maintain the reference to any module.

For e.g. There is one EventManager class that has event declaration and
public functions that raise events. So any other class that needs to
publish
data to interested classes, can call the event raiser method of the
EventManager class. The interested classes would already by handling the
event and will get the notification/data.

Public Class EventManager

Public Shared Event m_Notification()

Public Shared Sub NotificationRaiser()

RaiseEvent m_Notification()

End Sub

End Class
Thats fine and working. Now the problem is that the Event raising
mechanism
in .NET is synchronous so in above example the control wont leave the
NotificationRaiser until all classes that handle the notification have
done
their task. I would like this to be on separate thread (as much
automatically as possible - dont wanna do the plumbing myself).

So is there any way to raise some event asynchronously (like on some other
thread) without the reference of the class that is handling the event.

I hope I made myself clear, if there are still any queries .. then plz
lemme
know.

Any suggestion or reference is welcome.

Thanx
rawCoder

Nov 21 '05 #5

This discussion thread is closed

Replies have been disabled for this discussion.