2011-04-11 116 views
3

这可能非常简单,我没有看到它,因为这是漫长一天的结束,如果是我提前道歉。C#= MenuItem.Click处理程序 - 获取上下文菜单所属的对象?

我有一组按钮,当右键单击时弹出一个ContextMenu。该菜单有两个MenuItem,它们都有一个Click处理函数分配。我触发文本菜单弹出按钮上的右键像这样:

过于简化的例子:


public void InitiailizeButtonContextMenu() 
{ 
    buttonContextMenu = new ContextMenu(); 
    MenuItem foo = new MenuItem("foo"); 
    foo.Click += OnFooClicked; 

    MenuItemCollection collection = new MenuItemCollection(buttonContextMenu); 
    collection.Add(foo); 
} 

public void OnButtonMouseClick(object sender, MouseEventArgs e) 
{ 
    if (e.Button == MouseButtons.Left) 
     // left click stuff handling 
    if (e.Button == MouseButtons.Right) 
     buttonContextMenu.Show((Button)sender, new Point(e.X, e.Y)); 
} 


public void OnFooClicked(object sender, EventArgs e) 
{ 
    // Need to get the Button the ContextMenu .Show'd on in 
    // OnButtonMouseClick... thoughts? 
} 


ContextMenu buttonContextMenu; 

我需要能够得到触发文本菜单的按钮在MenuItem的Click处理程序中弹出,或以某种方式获取它。 MenuItem.Click采用EventArgs,因此在那里没有用。我可以将对象发送者重新映射回MenuItem,但是我找不到任何能告诉我是什么让它弹出的东西。这可能吗?

+0

这是WinForms或WPF的问题吗? – 2011-04-12 00:03:11

回答

7

使用ContextMenu.SourceControl属性,它给你一个Button实例的引用。

+3

值得注意的是(如果有人遇到同样的问题会遇到这个问题)你必须做的: Button parent =(Button)((ContextMenu)((MenuItem)sender).Parent)。 SourceControl; 从MenuItem一路回到按钮,但这是有效的!谢谢。 – trycatch 2011-04-12 13:59:42

+1

如果像我这样的人需要这个wpf,应该使用PlacementTarget属性:Button btn =(Button)((ContextMenu)((MenuItem)sender).Parent).PlacementTarget; – SepehrM 2013-12-27 17:18:22

0


Button buttonThatTriggeredTheContextMenu; 

public void OnButtonMouseClick(object sender, MouseEventArgs e) 
{ 
    if (e.Button == MouseButtons.Left) 
     // left click stuff handling 
    if (e.Button == MouseButtons.Right) { 
     buttonThatTriggeredTheContextMenu = (Button)sender; 
     buttonContextMenu.Show((Button)sender, new Point(e.X, e.Y)); 
    } 
} 


public void OnFooClicked(object sender, EventArgs e) 
{ 
    //buttonThatTriggeredTheContextMenu contains the button you want 
} 

2

在上面的代码片段,当你调用buttonContextMenu Show方法,您通过按钮对象buttonContextMenu,当您在按钮上单击鼠标右键。

要访问OnFooClicked方法中的按钮,只需将'发件人'转换回按钮即可。

public void OnFooClicked(object sender, EventArgs e) 
{ 
    ((MenuItem)sender).Parent //This is the button 
} 

*我不知道,如果菜单项是正确的投,但它应该是沿着这些线路。

+0

我现在远离我的代码,但我90%确定我尝试了这一点,并且它抛出了一个异常,因为发件人是MenuItem,因为它是一个MenuItem.Click处理程序。 – trycatch 2011-04-11 23:09:51

+0

哎呀,对不起。是的,这是行不通的。你应该能够引用父母,那将是你的按钮。抱歉。 – 2011-04-12 05:50:35

+0

MenuItem的父项是菜单。 – trycatch 2011-04-12 13:57:42

0

我不是100%的 - 它来自我2年前写的代码,但我希望它能让你继续这样做。

MenuItem item = (MenuItem)sender; 
DependencyObject dep = item.Parent; 
while((dep != null) && !(dep is Button)) 
    dep = VisualTreeHelper.GetParent(dep); 

if (dep == null) 
    return; 
Button button = dep as Button; 
0
button mybutton = ((ContextMenu)((MenuItem)sender).Parent).SourceControl as button; 
1

如果您正在使用的ContextMenuStrip及ToolStripItem的,而不是文本菜单和菜单项,你需要:

private void myToolStripMenuItem_Click(object sender, EventArgs e) 
{ 
    Button parent = (Button)((ContextMenuStrip)((ToolStripItem)sender).Owner).SourceControl; 
    ... 

一个普通文本菜单和菜单项(从汉斯帕桑特的帖子trycatch的评论):

Button parent = (Button)((ContextMenu)((MenuItem)sender).Parent).SourceControl;