views:

90

answers:

4

Hi,

Is it possible to set, on a control (a linkbutton for example) an eventhandler which is not in the same context as the control creation?

For example, I have an instance of Class1 which instances Class2, the control is created in Class2, but I need the eventhandler to be in Class1.

Pseudo Code:

public class Class1
{
    public Class1()
    {
        Class2 MyClass2 = new Class2();
        MyClass2.DoSomething();
    }

    public void EventHandler()
    {
        // Handle the event
    }
}

public class Class2
{
    public void DoSomething()
    {
        SomeControl control = new SomeControl();
        control.SomeEvent += parent.EventHandler;
    }
}

Regards Moo

A: 

Modifying darin's code:

public class Class1 
{
    public Class1()
    {
        Class2 class2 = new Class2();
        class2.Control.SomeEvent += this.EventHandler;
    }

    public EventHandler()
    {
        //DoStuff
    }
}

public class Class2
{
    public Control control;
}
erelender
A: 
public class Class1 
{
    public Class1()
    {
        new Class2().CreateControl(EventHandler);
    }

    public void EventHandler() {}
}

public class Class2
{
    public void CreateControl(Action eventHandler)
    {
        SomeControl control = new SomeControl();
        control.SomeEvent += eventHandler;
    }
}
Darin Dimitrov
erelender
Ahh, close but not what I am after. Class 1 will instantiate Class 2 so Class 2 is a child of Class 1, and call a method on the Class 2 instance which will create the controls. However, I then somehow need to set the control eventhandler in Class 2 to the eventhandler method in the parent Class 1.
Moo
Modified my sample accordingly.
Darin Dimitrov
+1  A: 

Have your Class2 expose a custom public event. This event is triggered when the control event fires.

// In Class2

    public event EventHandler<EventArgs<T>> ControlClickedEvent = null;

    protected void OnControlClickedEvent()
    {
        if (ControlClickedEvent != null)
        {
            ControlClickedEvent(this, new EventArgs());  
        }
    }

  ...

   private void cmdButton_Click(object sender, EventArgs e)
   {
        OnControlClickedEvent();
   }

Then have your Class1 subscribe to that event. The "event handler" is part of Class1.

// In Class1
MyClass2.ControlClickedEvent += new EventHandler<EventArgs<ControlClickedEvent>>(EventHandler);

If you are using multiple threads, ensure you use the InvokeRequired and BeginInvoke / Invoke methods in the code of the eventhandler in Class1.

Ash
A: 

I have fallen out of favor of using straight events in C# these days for most communication like this. I prefer a more decoupled communication pattern, like the "Event Aggregator" which has many benefits over traditional event hooking. They include:

  • Reduced coupling (Class1 and Class2 don't need to know about each other)
  • Reduced event storms
  • Weak hookups (no memory leaks if you forget to disconnect)
  • Filtering
Brian Genisio