必须单击上下文菜单项两次才能消失

时间:2019-09-12 15:14:31

标签: c# forms winforms event-handling contextmenu

我正在列表视图上创建一个上下文菜单,以便能够对特定项目执行功能。右键单击时,上下文菜单会正确显示,部分功能会执行,但不会完全执行,并且上下文菜单会再次显示。

我尝试在表单的加载功能中移动上下文菜单的创建和绑定,但是似乎不起作用...

private JsonReport _lastItemTag;

public Form1()
{
    InitializeComponent();
}

private void ReportTemplateManager_Load(object sender, EventArgs e)
{
    // Initialize context menu for template control
    ContextMenu cm = new ContextMenu();
    cm.MenuItems.Add("Load", new EventHandler(LoadReport_Click));
    template_listview.ContextMenu = cm;
}

private void Template_listview_MouseClick(object sender, MouseEventArgs e)
{
    bool match = false;
    if (e.Button == MouseButtons.Right)
    {
        foreach (ListViewItem item in template_listview.Items)
        {
            if (item.Bounds.Contains(new Point(e.X, e.Y)))
            {
                template_listview.ContextMenu.Show(template_listview, new Point(e.X, e.Y));
                match = true;
                _lastItemTag = item.Tag as JsonReport;
                break;
            }
        }
        if (!match)
            _lastItemTag = null;
    }
}

下面的函数被执行,但是没有关闭表单,我必须再次单击它以关闭上下文菜单和表单本身...

private void LoadReport_Click(object sender, EventArgs e)
{
    if (_lastItemTag != null)
    {
        Console.WriteLine("Loading"); // This get executed
        _lastItemTag = null;
        this.Close(); // This doesnt close the form on the first time
    }
}

我不明白为什么LoadReport函数可以“部分”执行而不关闭表格的原因。

1 个答案:

答案 0 :(得分:1)

您似乎在两次显示菜单。

通过将上下文菜单分配给ContextMenu属性,右键单击列表视图时,菜单将自动打开。无需手动显示菜单。

此外,无需遍历菜单项即可找到匹配项。我什至不确定您要通过处理列表视图的MouseClick事件来做什么。我认为您可以完全消除该方法。

菜单项事件处理程序的sender自变量包含被单击的菜单项。您只需投射它并从那里获取Tag属性:

private JsonReport _lastItemTag;

public Form1()
{
    InitializeComponent();
}

private void ReportTemplateManager_Load(object sender, EventArgs e)
{
    // Initialize context menu for template control
    ContextMenu cm = new ContextMenu();

    //The event handler will be called when this menu item is clicked.
    cm.MenuItems.Add("Load", new EventHandler(LoadReport_Click));

    template_listview.ContextMenu = cm;
}

private void LoadReport_Click(object sender, EventArgs e)
{
    //The 'sender' argument is the menu item that was clicked
    //In this case, it is the Load menu item so cast the sender
    var menuItem = sender as MenuItem;

    //Now get the Tag property and cast it to JsonReport
    _lastItemTag = menuItem.Tag as JsonReport;

    if (_lastItemTag != null)
    {
        Console.WriteLine("Loading"); // This get executed
        this.Close(); // This doesnt close the form on the first time
    }
}