2008-02-13

Sharing Menu Items between ToolStrips on a Windows Form

So, you may have found yourself building a nice user-friendly, somewhat complicated Windows Forms application, that had lots of drop-down menus and right click context menus, and what not.. You may have naively assumed that you could *share* your menu items, so that you have a consistent set of options, icons, and more importantly event handlers for a particular menu item or set of menu items.


Well, I did... I had a Tools drop-down menu with some basic functions that I wanted to also be accessible from a right-click content menu on a treeview. Redundant? Sure... Convenient? Definately.

There's a little annoying detail that says that a ToolStripMenuItem can't be "owned" by more than one ToolStrip. In other words, it can only be in one place at a time. So, when you do something like this:

toolsToolStripMenuItem.DropDownItems.Add(myMenuItem);
treeNodeContextToolStrip.Items.Add(myMenuItem);

The menu item in question suddenly disappears from the tools menu, and appears in the content menu... Hmm...

So, in order to share the menu item, I came up with this hackish solution....I handled the Opening event for the two menu strips and in each one, "took ownership" of the menuitem. So, through sleight-of-hand it seems to exist in one place at a time. We can only get away with this because, ToolStrips, being modal, only show one at a time.

So, here's a simple sample:

Hot-Swap Menu Item Sample

private void treeNodeContextMenuStrip_Opening(object sender, CancelEventArgs e)
{
treeNodeContextMenuStrip.Items.Insert(3, myToolStripMenuItem);
}

private void toolsToolStripMenuItem_DropDownOpening(object sender, EventArgs e)
{
this.toolsToolStripMenuItem.DropDownItems.Insert(5, this.myToolStripMenuItem);
}