繁体   English   中英

单击 MenuItem 时,WinForms ContextMenu 保持打开状态

[英]WinForms ContextMenu stays open when MenuItem is clicked

所以我有一个表单 DataGridView,当我右键单击网格时,我想显示一个上下文菜单,其中包含一个菜单项。 该菜单项将打开第二个窗体,该窗体将为 DataGridView 提供一些配置选项。

现在所有这些都工作得很好,上下文菜单正确显示,第二个表单正确打开,该表单上的所有功能都正常工作。

唯一的问题是上下文菜单只有在我单击菜单项以外的任何地方时才会关闭。 无论我单击菜单项多少次,上下文菜单都不会关闭。

我曾尝试寻找解决方法,但据我所知,无法以编程方式关闭上下文菜单。

任何帮助将不胜感激。 下面是用于打开上下文菜单和菜单项单击事件的单击事件的副本。

private void DataGridView_CellMouseClick(object sender, DataGridViewCellMouseEventArgs e)
{
    if (e.Button == MouseButtons.Right)
    {
        DataGridView dgv = (DataGridView)sender;
        if (dgv.CurrentCell == null)
        {
            return;
        }
        else
        {
            Rectangle r = dgv.GetCellDisplayRectangle(e.ColumnIndex, e.RowIndex, false);
            Point p = new Point(r.X + e.X, r.Y + e.Y);
            ContextMenu cm = new ContextMenu();
            cm.MenuItems.Add(new MenuItem("Item", Item_Click));
            cm.Show(dgv, p);
        }
    }
}

private void Item_Click(object sender, EventArgs e)
{
    new SecondForm().Show();
}

更新:我通过用 ContextMenuStrip 类替换 ContextMenu 类、删除 MouseClick 事件处理程序并将 ContextMenuStrip 对象分配给 DataGridView.ContextMenuStrip 解决了这个问题。 看起来好像 ContextMenuStrip 类在相关控件被右键单击时处理显示菜单,因此如果您添加单击事件处理程序来处理打开菜单,它将反复尝试渲染菜单,使其在显示之前闪烁多次最终呈现

在您的课程中添加一个私有变量

private bool CloseMenu = true;

鼠标按下上下文菜单

private void Item_Click(object sender, EventArgs e)
{
    CloseMenu = false;
    new SecondForm().Show();
}

添加上下文菜单关闭事件

private void contextMenuStripMy_Closing(object sender, ToolStripDropDownClosingEventArgs e)
{
    e.Cancel = !CloseMenu;
    CloseMenu = true;
}

经过多次试验,我找到了一些解决此问题的方法。

首先,这是关于 ContextMenu 而不是 ContextMenuStrip。

这不是完美的解决方案,但如果您没有其他替代解决方案,它会很好用。

这是如何。

只需为上下文菜单下的所有菜单项设置 Visiable = false。

唯一的问题是它在鼠标周围显示小方块。

我认为这个小方块是空的上下文菜单框。

但是,如果用户点击任何地方并且上下文菜单失去焦点,这个小方块将被快速删除。

它真的很小而且不打扰。

在代码中,如果您只有一个菜单项,则这看起来像这样。

                 if (cm != null)
                {
                    if (cm.MenuItems.Count > 0) cm.MenuItems[0].Visible = false;
                }

如果您有多个项目,则只需循环遍历所有菜单项。

                 if (cm != null)
                {
                    for(int i = 0; i < cm.MenuItems.Count ; i++)
                     cm.MenuItems[i].Visible = false;
                }

希望这可以帮助。

它适用于我的情况。

所以我不必从 ContextMenu 切换到 ContextMenuStrip。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM