1

So what I'm basically trying to do is create a dynamic menu framework in C#. I essentially have a menu element (just a rectangle with some text on it at this point), which contains a DoAction() method. This method is run whenever the rectangle is clicked. What I want is for the DoAction method to be able to be defined at runtime. So for example I could instantiate a menu element whose DoAction() method does function x(), then instantiate another menu element whose DoAction() method does function y(). What I have is something like this.

public class MenuElement {
    public void DoAction(); // method I want to be dynamic

    public MenuElement((text, height, width, etc), method myMethod){
        DoAction = myMethod;
    }
}

MenuElement m1 = new MenuElement(..., function x());
MenuElement m2 = new MenuElement(..., function y());

m1.DoAction(); // calls x()
m2.DoAction(); // calls y()

This is the kind of thing that I know how to do in Javascript, but I'm not as familiar with C#, and I suspect .Net will make me jump through a few more hoops than JS would. From what I'm reading I'm going to have to use delegates? I can't find any tutorials that I can really follow to easily.

2 Answers 2

2

Use the Action-Class. In your example it would be:

public class MenuElement {
public Action DoAction; // method I want to be dynamic

public MenuElement((text, height, width, etc), Action myMethod){
    DoAction = myMethod;
}
}

MenuElement m1 = new MenuElement(..., new Action(() => {
// your code here
});

MenuElement m2 = new MenuElement(..., new Action(() => {
// your code here
));

m1.DoAction(); // calls x()
m2.DoAction(); // calls y()

For more information see MSDN

Sign up to request clarification or add additional context in comments.

3 Comments

Awesome, this is exactly what I was looking for! Do I have to use a lambda expression every time? Or would I be able to pass in an already existing method? Say, something like new Action(myAlreadyExistingMethod());
After a quick test: yes you can. For anyone wondering its as simple as new Action(myAlreadyExistingMethod); // no brackets after method name
Thanks for the accepted answer. I hope I could help :)
1

Yes, delegates are the way to go. You can make use of different flavours of the delegates Action and Func for your requirement. Is this what you are trying to achieve?

public class MenuElement
{
    public MenuElement(string text, int height, int width, Action<object> myMethod)
    {
        DoAction = myMethod;
    }

    public Action<object> DoAction { get; private set; }
}

        MenuElement m1 = new MenuElement("text", 10, 20, (obj) => { Console.WriteLine("MenuElement1"); });
        m1.DoAction(null);


        Action<object> y = (obj) =>
        {
            Console.WriteLine("MenuElement2");
        };

        MenuElement m2 = new MenuElement("text", 10, 20, y);
        m2.DoAction(null); // calls y()

2 Comments

You're a gentleman and a scholar, sir. This is a great answer. It gives extra syntactical goodness. Only reason I gave Jordan the tick was because I liked his syntax more (DoAction(null) seems a bit cumbersome).
As I mentioned in my answer there are different flavours of Action and Func that can be used based on the input parameters and output that you want to return from your DoAction. If there is no input parameter then you use simple Action. Glad that I could help.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.