C# - 将 ContextMenuStrip 项目复制到另一个

C# - Duplicate ContextMenuStrip Items into another

我在 Windows 表单应用程序中有两个 ContextMenuStrip,其中一个有 3 个项目,另一个有 none.

让我们假设:

ContextMenuStrip c1 = new ContextMenuStrip();
ContextMenuStrip c2;

c1 有 3 个 ToolStripMenuItems,c2 是 ContextMenuStrip 应该复制 c1 项目的目的地。

我试着写这个:

c2 = new ContextMenuStrip(c1.Container);

但它给了我一个 ArgumentNullException 因为 c1.Container 等于 null.

我不知道如何解决这个问题,你能帮我吗?

Ps。 我会 new ToolStripMenuItem(s),没有参考文献

whileforeach 循环解决方案不是执行此操作的最佳方法。

谢谢:)

您需要创建一个新的 ContextMenuStrip 并将 Item(不是 c1Container 添加到新菜单中:

c2 = new ContextMenuStrip();
c2.Items.AddRange(c1.Items);

但请注意,这不会重复 项目。 相同的项目实例 现在在两个菜单中。

如果要克隆它们,这会相当复杂,因为您必须处理项目的特定类型、要克隆的属性,尤其是事件处理程序。

一个简单的例子可以是:

c2.Items.AddRange(c1.Items.OfType<ToolStripItem>()
                           .Select(item => new ToolStripMenuItem(item.Text))
                           .OfType<ToolStripItem>().ToArray());

第二个 OfType 是必要的,以避免从 ToolStripMenuItem[]ToolStripItem[] 的协变数组转换,这是 AddRange() 所期望的。


附带说明:Container 包含 菜单的组件(这就是为什么 null 当菜单未显示时)而不是菜单保留其项目的东西。

然后,创建一个创建 ContextMenuStrip 的函数,并在每次需要新菜单时调用它

Func<ContextMenuStrip> newContextMenuStrip = () => { 
    var c = new ContextMenuStrip();
    c.Items.Add("item 1");
    c.Items.Add("item 2");
    c.Items.Add("item 3");
    return c;
};

var c1 = newContextMenuStrip();
var c2 = newContextMenuStrip();

晚会迟到了,但我过去遇到过同样的问题并找到了一个相当简单的解决方案。

假设您的 toolStripMenuItem 在上下文菜单中声明为 'TSMI_open', 您可以在上下文菜单打开时有效地对其进行热交换。 像这样:

void Context1_Opening(object sender, CancelEventArgs e)
{
     Context1.Items.Insert(0, TSMI_open);
}

void Context2_Opening(object sender, CancelEventArgs e)
{
     Context2.Items.Insert(0, TSMI_open);
}

菜单项无缝出现在两个菜单上,连续打开同一个菜单两次不会出错。