There is as of .NET 2.0 a generic EventHandler delegate type, which can be used to define an event in terms of the EventArgs type you wish to use, without having to create a redundant delegate type to use in the event declaration.Well, what about the EventArgs? I often find myself having to create one-offs derived from EventArgs to encapsulate extra data I wish to send. Why can't that be declared generically as well? If all I need to pass is a string, or an integer, or a Point, why do I have to create a StringEventArgs, IntEventArgs and/or PointEventArgs class respectively?I roughed up two very basic EventArgs generic types as a proof-of-concept: public class ReadOnlyEventArgs<T>:EventArgs{    public T Parameter { get; private set; }    public ReadOnlyEventArgs(T input)    {        Parameter = input;    }}public class EventArgs<T>:EventArgs{    public T Parameter { get; set; }    public EventArgs(T input)    {        Parameter = input;    }}The obvious difference is whether you want event handlers to be able to modify your arguments. Sometimes it's a good idea, most of the time not so good. Usage would simply look like:public event EventHandler<EventArgs<string>> StringValidationRequested;public event EventHandler<ReadOnlyEventArgs<int>> RecordSelectedForRetrieval;public event EventHandler<ReadOnlyEventArgs<Point>> MouseLocationReported;Now, obviously these are for simpler situations, but I've found most situations of event raising to be pretty simple. The only possible thing I'd add would be two more classes derived from CancelEventArgs to add that additional functionality. The fact that the Parameter can be anything including a class makes it flexible enough to pass complex data, and .NET 4's Tuples take care of the remaining situations where you might not want to define your own complex type. The only drawback I can think of is not being able to descriptively name your parameter; it's generic.
Generic EventArgs to go with generic EventHandler?
c#;event handling
You could make it a little bit more useful if you added some supporting factory methods to create the arguments.  That way you don't have to use the constructor and its somewhat awkward syntax (having to supply the types).public static class EventHandlerExtensions{    public static EventArgs<T> CreateArgs<T>(        this EventHandler<EventArgs<T>> _,        T argument)    {        return new EventArgs<T>(argument);    }    public static ReadOnlyEventArgs<T> CreateArgs<T>(        this EventHandler<ReadOnlyEventArgs<T>> _,        T argument)    {        return new ReadOnlyEventArgs<T>(argument);    }}Then to create the instance of the arguments, you could just do this:public event EventHandler<EventArgs<SomeArg>> SomeEvent;public event EventHandler<ReadOnlyEventArgs<SomeArg>> SomeOtherEvent;protected virtual void OnSomeEvent(SomeArg argument){    var someEvent = SomeEvent;    if (someEvent != null)    {        var args = someEvent.CreateArgs(argument);        // instead of:        //var args = new EventArgs<SomeArg>(argument);        someEvent(this, args);    }}protected virtual void OnSomeOtherEvent(SomeArg argument){    var someOtherEvent = SomeOtherEvent;    if (someOtherEvent != null)    {        var args = someOtherEvent.CreateArgs(argument);        // instead of:        //var args = new ReadOnlyEventArgs<SomeArg>(argument);        someOtherEvent(this, args);    }}It might be useful to have options for multiple parameters (similar to how the tuple is).  Though it might not be feasible to have all combinations of multiple (im)mutable arguments.