2

I want to be able to right click on an image and for there to be a menu show up. When I then click on one of the items I want it to point to a class:

    private void link1add_MouseDown(object sender, MouseEventArgs e)
    {
        if (e.Button == MouseButtons.Right)
        {
        ContextMenu cm = new ContextMenu();
        cm.MenuItems.Add("Add", HandleContextMenuAdd);
        cm.MenuItems.Add("Remove", HandleContextMenuRemove); 
        link1add.ContextMenu = cm;
        }
    }
        private void HandleContextMenuAdd(object sender, EventArgs e) 
        { 
            MessageBox.Show("Adding");
        }
        private void HandleContextMenuRemove(object sender, EventArgs e)
        {
            MessageBox.Show("Removing");
        }

Code edited since first posted. Thanks all for your help.

Marshal
  • 1,177
  • 4
  • 18
  • 30

3 Answers3

1

What about a lambda expression?

cm.MenuItems.Add("Item 2", (_, __) => { 
  if (...) ReadDocument();
});

or

cm.MenuItems.Add("Item 2", (_, __) => { this.myClassInstance.DoSomething(); });

Alternatively, you can create a method with the signature of the expected event handler:

cm.MenuItems.Add("Item 2", HandleContextMenuClick);

private void HandleContextMenuClick(object sender, EventArgs e)
{
  if (...) ReadDocument();
}

That method doesn't need to be in the same class (you can write this.myClassInstance.HandleContextMenuclick for example). But I would hide the implementation detail from other classes to avoid unnecessary coupling.

Gene
  • 4,192
  • 5
  • 32
  • 56
  • I used the method - I can't beleive how simple it is! I have two handling events though. Not sure if I need to do it like that but I have updated my code accordingly. However is it possible to have one event? But have an if statement or switch to select which item has been selected? I will look into the lambda methods later on as they do look useful. Thank you. – Marshal Mar 26 '12 at 11:56
  • @Marshal, yes it's possible to use the same event for as many menu items as you want. You can find that in my answer. – Brad Rem Mar 26 '12 at 14:34
1

Pattern for your own code after this:

    public class ReadDocumentEventArgs : EventArgs
    {
        public string ImageInfo { get; set; }
    }

    public void ReadDocument(object sender, ReadDocumentEventArgs ea)
    {
        // do whatever you need to do
        MessageBox.Show(ea.ImageInfo);  // example
    }

    private void link1add_MouseDown(object sender, MouseEventArgs e)
    {
        if (e.Button == MouseButtons.Right)
        {
            PictureBox imageCtrl = sender as PictureBox;

            // get the information you need to get from your control to identify it
            string imgInfo = "Hello, World!"; // example

            ContextMenu cm = new ContextMenu();
            cm.MenuItems.Add("Item 1");
            cm.MenuItems.Add("Item 2", 
               (EventHandler)((s, rde) => 
               { ReadDocument(s, new ReadDocumentEventArgs() 
                  { ImageInfo = imgInfo }); 
               }));

            link1add.ContextMenu = cm;
        }
    }

In your MouseDown over your image you can create a menu item using the code I supplied above that will call an event handler called ReadDocument. Notice that there is a ReadDocumentEventArgs class that you can customize to contain the necessary properties that will help you identify which image you have clicked on.

So, in the example I have above one of the first things that happens in MouseDown is that you get the instance of image control (I assume it's a Picture Box, but you can cast it to whatever it really is).

At that point, you can then get a file name or whatever from your image that identifies it from the other controls on your form.

Next, when creating a context menu item, it tells the menu item to call ReadDocument but passes in the special data just taken from the image control.

In the ReadDocument method, you can then do whatever you need to do. In my example, I simply throw up a MessageBox to show you what data you passed in.

Brad Rem
  • 6,036
  • 2
  • 25
  • 50
0

What you will want is to put another event handler and call your readdocument method.

Daniel A. White
  • 187,200
  • 47
  • 362
  • 445
  • Sounding newbie here. The reason I wanted to call the class is because I have never dealt with creating my own events before and even with links of help they never relate to what I want to do so I am unable to comprehend how to create one for my needs. But thanks for your help. – Marshal Mar 22 '12 at 15:25
  • Does `cm.MenuItems.Add("Item 3" new EventHandler(readDocumentMethodNameGoesHere));` not work? – Bridge Mar 22 '12 at 15:31