Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to put a ContextMenu into the header of a TabPage

I have a custom TabControl in which I have TabPages with ContextMenu bound to them.

I want the menu to show up only when the page header is being clicked.

What I do is that, when the TabControl is clicked, I check these conditions:

private void MouseUp(object sender, MouseEventArgs e) 
{
    if (e.Button == Mousebuttons.Right) 
    {
        for (int i = 0; i < TabCount; ++i) 
        {
            Rectangle r = GetTabRect(i);
            if (r.Contains(e.Location) /* && it is the header that was clicked*/) 
            {
                // Change slected index, get the page, create contextual menu
                ContextMenu cm = new ContextMenu();
                // Add several items to menu
                page.ContextMenu = cm;
                page.ContextMenu.Show(this, e.Location);
            }
        }
    }
}

If I bind MouseUp to the TabControl, I get the ContextMenu in the entire TabPage. If I bind it to the TabPage, I only get the ContextMenu in the body and not in the header.

Is there a way to have a ContextMenu to show up only on header Click ?

like image 764
Francis.Beauchamp Avatar asked Jun 04 '13 17:06

Francis.Beauchamp


2 Answers

Just don't ever assign the ContextMenu to anything...simply display it:

public class MyTabControl : TabControl
{

    protected override void OnMouseUp(MouseEventArgs e)
    {
        if (e.Button == System.Windows.Forms.MouseButtons.Right)
        {
            for (int i = 0; i < TabCount; ++i)
            {
                Rectangle r = GetTabRect(i);
                if (r.Contains(e.Location) /* && it is the header that was clicked*/)
                {
                    // Change slected index, get the page, create contextual menu
                    ContextMenu cm = new ContextMenu();
                    // Add several items to menu
                    cm.MenuItems.Add("hello");
                    cm.MenuItems.Add("world!");
                    cm.Show(this, e.Location);
                    break;
                }
            }
        }
        base.OnMouseUp(e);
    }

}
like image 147
Idle_Mind Avatar answered Oct 05 '22 22:10

Idle_Mind


Instead of override like Idle_Mind said, you could also do the same with a normal tabcontrol on the mouseevent:

    private void tabControl1_MouseClick(object sender, MouseEventArgs e)
    {
        if (e.Button == System.Windows.Forms.MouseButtons.Right)
        {
            for (int i = 0; i < tabControl1.TabCount; ++i)
            {
                Rectangle r = tabControl1.GetTabRect(i);
                if (r.Contains(e.Location) /* && it is the header that was clicked*/)
                {
                    // Change slected index, get the page, create contextual menu
                    ContextMenu cm = new ContextMenu();
                    // Add several items to menu
                    cm.MenuItems.Add("hello");
                    cm.MenuItems.Add("world!");
                    cm.Show(tabControl1, e.Location);
                    break;
                }
            }
        }
    }

It does exactly the same, but doesn't add an extra control in your toolbox:) You could also make it generic if you want to use it on multiple TabControls.

    private void showContextMenu_MouseClick(object sender, MouseEventArgs e)
    {
        if (e.Button == System.Windows.Forms.MouseButtons.Right)
        {
            TabControl tabControl1 = sender as TabControl;
            [...]
like image 44
Gideon Mulder Avatar answered Oct 05 '22 20:10

Gideon Mulder