Set Statusbar Text on Mouse Hover - Works for controls but not MenuItems
I devised the following code for displaying a control's Tag property on mouseover. The code works fine for standard controls such as Labels and TextBoxes but I cannot get it to work for my MenuItems (more specifically ToolStripMenuItems). Could y'all please take a look at my code and tell me what I did wrong? Thanks in advance!
public void Form1_Load(object sender, EventArgs e)
{
...
this.addEventsToAllComponents(this);
}
private void addEventsToAllComponents(Com开发者_运维百科ponent component)
{
if (component is MenuItem)
{
MenuItem menuItem = component as MenuItem;
menuItem.Select += new EventHandler(menuItem_Select);
}
else if (component is Control)
{
Control ctrl = component as Control;
foreach (Control control in ctrl.Controls)
{
control.MouseEnter += new EventHandler(this.control_MouseEnter);
control.MouseLeave += new EventHandler(this.control_MouseLeave);
if (control.HasChildren)
addEventsToAllComponents(control);
}
}
}
private void menuItem_Select(object sender, EventArgs e)
{
MenuItem menuItem = sender as MenuItem;
if (menuItem.Tag.ToString().Length > 0)
this.toolStripStatusLabel1.Text = menuItem.Tag.ToString();
}
private void control_MouseEnter(object sender, EventArgs e)
{
Control control = sender as Control;
if (control.Tag.ToString().Length > 0)
this.toolStripStatusLabel1.Text = control.Tag.ToString();
}
private void control_MouseLeave(object sender, EventArgs e)
{
if (this.toolStripStatusLabel1.Text.ToString().Length > 0)
this.toolStripStatusLabel1.Text = "";
}
There are a few problems with your code.
1st. The Items of a MenuStrip are not children of the Item, so HasChildren will return false. Instead, they are in the Items collection of the MenuStrip. You need to handle a MenuStrip occurrence specially. Add the following code in your AddEvents... method below:
(snip...)
// old code
if (control.HasChildren)
AddEventsToAllControls(control);
//add new code below
if (control is MenuStrip) {
MenuStrip ms = control as MenuStrip;
AddEventsToAllToolStripMenuitems(ms.Items);
}
And add the new method as follows:
private void AddEventsToAllToolStripMenuitems (ToolStripItemCollection items) {
foreach (ToolStripItem tsi in items) {
tsi.MouseEnter += new EventHandler(this.control_MouseEnter);
tsi.MouseLeave += new EventHandler(this.control_MouseLeave);
if (tsi is ToolStripMenuItem) {
ToolStripMenuItem mi = tsi as ToolStripMenuItem;
AddEventsToAllToolStripMenuitems(mi.DropDownItems);
}
}
}
2nd. ToolStripItem doesn't derive from Control, so in MouseEnter the sender as Control statement will fail (control will be null). Do something like this:
Control control = sender as Control;
if (control != null && control.Tag != null && control.Tag.ToString().Length > 0)
this.toolStripStatusLabel1.Text = control.Tag.ToString();
ToolStripItem tsi = sender as ToolStripItem;
if (tsi != null && tsi.Tag != null && tsi.Tag.ToString().Length > 0)
this.toolStripStatusLabel1.Text = tsi.Tag.ToString();
(I also added some null checks)
This should get you going.
You don't have any code to handle ToolStripMenuItems
- They are not derived from MenuItems
, so your MenuItem-handling code won't do anything for them.
Aside: for readability, you might like to use string.IsNullOrEmpty(menuItem.Tag.ToString())
to test for empty/blank strings.
You don't have the recursion set up for MenuItems
that contain other menu items. So when it find a menuitem, it will only add the top level MenuItem
, not it's children.
try adding:
foreach (MenuItem item in menuItem.MenuItems)
{
item Select += new EventHandler(menuItem_Select);
if (item.IsParent)
addEventsToAllComponents(item);
}
in the section for handling MenuItems
.
Here is the revised code for AddEventsToAllComponents method:
private void addEventsToAllControls(Control ctrl)
{
foreach (Control control in ctrl.Controls)
{
control.MouseEnter += new EventHandler(this.control_MouseEnter);
control.MouseLeave += new EventHandler(this.control_MouseLeave);
if (control.HasChildren)
addEventsToAllControls(control);
if (control is MenuStrip)
{
MenuStrip ms = control as MenuStrip;
AddEventsToAllToolStripItems(ms.Items);
}
else if (control is ToolStrip)
{
ToolStrip ts = control as ToolStrip;
AddEventsToAllToolStripItems(ts.Items);
}
}
}
精彩评论