2011-06-12 70 views
2

与此类似问题的控制(TreeView控件): get contextmenustrip from toolstripmenuitem获得由toolstripmenuitem事件处理

只是现在我需要找到其上下文菜单中点击ToolStripMenuItem时打开的对象。

SourceControlParent,OwnerGetParentControl()都返回null。

最初我有一个TreeView,它的ContextMenuStrip属性被设置。

这里是我的初步代码:

 ToolStripMenuItem tsmi = (ToolStripMenuItem)sender; 
     ToolStripMenuItem tsmip = (ToolStripMenuItem)tsmi.OwnerItem; 
     ContextMenuStrip cms = (ContextMenuStrip)tsmip.GetCurrentParent(); 
     TreeView tv = (TreeView)cms.SourceControl; 
     // returns null, but not in the cms_openHandler 
     tv.Nodes.Add(new TreeNode("event fired.")); 

我是否获得了ContextMenuStrip不当?为什么cms的SourceControl属性在OpenHandler中工作,但不是来自ToolStripMenuItem事件处理程序?

Form1.Designer.cs:

namespace TestWFA 
{ 
partial class Form1 
{ 
    /// <summary> 
    /// Required designer variable. 
    /// </summary> 
    private System.ComponentModel.IContainer components = null; 

    /// <summary> 
    /// Clean up any resources being used. 
    /// </summary> 
    /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param> 
    protected override void Dispose(bool disposing) 
    { 
     if (disposing && (components != null)) 
     { 
      components.Dispose(); 
     } 
     base.Dispose(disposing); 
    } 

    #region Windows Form Designer generated code 

    /// <summary> 
    /// Required method for Designer support - do not modify 
    /// the contents of this method with the code editor. 
    /// </summary> 
    private void InitializeComponent() 
    { 
     this.components = new System.ComponentModel.Container(); 
     this.treeView1 = new System.Windows.Forms.TreeView(); 
     this.contextMenuStrip1 = new System.Windows.Forms.ContextMenuStrip(this.components); 
     this.expandToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem(); 
     this.childrenToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem(); 
     this.allDescendantsToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem(); 
     this.collapseToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem(); 
     this.childrenToolStripMenuItem1 = new System.Windows.Forms.ToolStripMenuItem(); 
     this.parentToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem(); 
     this.childrenToolStripMenuItem2 = new System.Windows.Forms.ToolStripMenuItem(); 
     this.allDescendantsToolStripMenuItem1 = new System.Windows.Forms.ToolStripMenuItem(); 
     this.contextMenuStrip1.SuspendLayout(); 
     this.SuspendLayout(); 
     // 
     // treeView1 
     // 
     this.treeView1.ContextMenuStrip = this.contextMenuStrip1; 
     this.treeView1.Location = new System.Drawing.Point(64, 75); 
     this.treeView1.Name = "treeView1"; 
     this.treeView1.Size = new System.Drawing.Size(262, 247); 
     this.treeView1.TabIndex = 0; 
     // 
     // contextMenuStrip1 
     // 
     this.contextMenuStrip1.Items.AddRange(new System.Windows.Forms.ToolStripItem[] { 
     this.expandToolStripMenuItem, 
     this.collapseToolStripMenuItem}); 
     this.contextMenuStrip1.Name = "contextMenuStrip1"; 
     this.contextMenuStrip1.Size = new System.Drawing.Size(153, 70); 
     this.contextMenuStrip1.Opening += new System.ComponentModel.CancelEventHandler(this.contextMenuStrip1_Opening); 
     // 
     // expandToolStripMenuItem 
     // 
     this.expandToolStripMenuItem.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[] { 
     this.childrenToolStripMenuItem, 
     this.allDescendantsToolStripMenuItem}); 
     this.expandToolStripMenuItem.Name = "expandToolStripMenuItem"; 
     this.expandToolStripMenuItem.Size = new System.Drawing.Size(152, 22); 
     this.expandToolStripMenuItem.Text = "Expand"; 
     // 
     // childrenToolStripMenuItem 
     // 
     this.childrenToolStripMenuItem.Name = "childrenToolStripMenuItem"; 
     this.childrenToolStripMenuItem.Size = new System.Drawing.Size(161, 22); 
     this.childrenToolStripMenuItem.Text = "Children"; 
     this.childrenToolStripMenuItem.Click += new System.EventHandler(this.childrenToolStripMenuItem_Click); 
     // 
     // allDescendantsToolStripMenuItem 
     // 
     this.allDescendantsToolStripMenuItem.Name = "allDescendantsToolStripMenuItem"; 
     this.allDescendantsToolStripMenuItem.Size = new System.Drawing.Size(161, 22); 
     this.allDescendantsToolStripMenuItem.Text = "All Descendants"; 
     this.allDescendantsToolStripMenuItem.Click += new System.EventHandler(this.allDescendantsToolStripMenuItem_Click); 
     // 
     // collapseToolStripMenuItem 
     // 
     this.collapseToolStripMenuItem.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[] { 
     this.childrenToolStripMenuItem1, 
     this.parentToolStripMenuItem, 
     this.childrenToolStripMenuItem2, 
     this.allDescendantsToolStripMenuItem1}); 
     this.collapseToolStripMenuItem.Name = "collapseToolStripMenuItem"; 
     this.collapseToolStripMenuItem.Size = new System.Drawing.Size(152, 22); 
     this.collapseToolStripMenuItem.Text = "Collapse"; 
     // 
     // childrenToolStripMenuItem1 
     // 
     this.childrenToolStripMenuItem1.Name = "childrenToolStripMenuItem1"; 
     this.childrenToolStripMenuItem1.Size = new System.Drawing.Size(161, 22); 
     this.childrenToolStripMenuItem1.Text = "All Ancestors"; 
     this.childrenToolStripMenuItem1.Click += new System.EventHandler(this.childrenToolStripMenuItem1_Click); 
     // 
     // parentToolStripMenuItem 
     // 
     this.parentToolStripMenuItem.Name = "parentToolStripMenuItem"; 
     this.parentToolStripMenuItem.Size = new System.Drawing.Size(161, 22); 
     this.parentToolStripMenuItem.Text = "Parent"; 
     this.parentToolStripMenuItem.Click += new System.EventHandler(this.parentToolStripMenuItem_Click); 
     // 
     // childrenToolStripMenuItem2 
     // 
     this.childrenToolStripMenuItem2.Name = "childrenToolStripMenuItem2"; 
     this.childrenToolStripMenuItem2.Size = new System.Drawing.Size(161, 22); 
     this.childrenToolStripMenuItem2.Text = "Children"; 
     this.childrenToolStripMenuItem2.Click += new System.EventHandler(this.childrenToolStripMenuItem2_Click); 
     // 
     // allDescendantsToolStripMenuItem1 
     // 
     this.allDescendantsToolStripMenuItem1.Name = "allDescendantsToolStripMenuItem1"; 
     this.allDescendantsToolStripMenuItem1.Size = new System.Drawing.Size(161, 22); 
     this.allDescendantsToolStripMenuItem1.Text = "All Descendants"; 
     this.allDescendantsToolStripMenuItem1.Click += new System.EventHandler(this.allDescendantsToolStripMenuItem1_Click); 
     // 
     // Form1 
     // 
     this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); 
     this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; 
     this.ClientSize = new System.Drawing.Size(406, 365); 
     this.Controls.Add(this.treeView1); 
     this.Name = "Form1"; 
     this.Text = "Form1"; 
     this.contextMenuStrip1.ResumeLayout(false); 
     this.ResumeLayout(false); 

    } 

    #endregion 

    private System.Windows.Forms.TreeView treeView1; 
    private System.Windows.Forms.ContextMenuStrip contextMenuStrip1; 
    private System.Windows.Forms.ToolStripMenuItem expandToolStripMenuItem; 
    private System.Windows.Forms.ToolStripMenuItem childrenToolStripMenuItem; 
    private System.Windows.Forms.ToolStripMenuItem allDescendantsToolStripMenuItem; 
    private System.Windows.Forms.ToolStripMenuItem collapseToolStripMenuItem; 
    private System.Windows.Forms.ToolStripMenuItem childrenToolStripMenuItem1; 
    private System.Windows.Forms.ToolStripMenuItem parentToolStripMenuItem; 
    private System.Windows.Forms.ToolStripMenuItem childrenToolStripMenuItem2; 
    private System.Windows.Forms.ToolStripMenuItem allDescendantsToolStripMenuItem1; 
} 
} 

Form1.cs中:

using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Data; 
using System.Drawing; 
using System.Linq; 
using System.Text; 
using System.Windows.Forms; 

namespace TestWFA 
{ 
public partial class Form1 : Form 
{ 
    public Form1() 
    { 
     InitializeComponent(); 
     treeView1.Nodes.Add(new TreeNode("root")); 
    } 

    private void childrenToolStripMenuItem1_Click(object sender, EventArgs e) 
    { 
     TreeView tv = GetSourceControl(sender) as TreeView; 

     if (tv != null) 
     { 
      tv.Nodes.Add("Tree event catched!"); 
     } 

     /*ToolStripMenuItem tsmi = (ToolStripMenuItem)sender; 
     ToolStripMenuItem tsmip = (ToolStripMenuItem)tsmi.OwnerItem; 


     ContextMenuStrip cms = (ContextMenuStrip)tsmip.GetCurrentParent(); 
     ToolStrip ts = tsmip.GetCurrentParent(); 

     IContainer c = cms.Container; 
     TreeView tv = (TreeView)c; 
     tv.Nodes.Add(new TreeNode("event fired."));*/ 
    } 

    private object GetSourceControl(object Sender) 
    { 
     if (Sender as ContextMenuStrip != null) 
     { 
      return ContextMenuStrip.SourceControl; 
     } 

     var item = Sender as ToolStripItem; 

     // move to root item 
     while (item.OwnerItem != null) 
     { 
      item = item.OwnerItem; 
     } 

     // we have root item now, so lets take ContextMenuStrip object 
     var menuObject = item.Owner as ContextMenuStrip; 

     if (menuObject != null) 
     { 
      return menuObject.SourceControl; 
     } 

     return null; 

    } 

    private void parentToolStripMenuItem_Click(object sender, EventArgs e) 
    { 

    } 

    private void childrenToolStripMenuItem2_Click(object sender, EventArgs e) 
    { 

    } 

    private void allDescendantsToolStripMenuItem1_Click(object sender, EventArgs e) 
    { 

    } 

    private void childrenToolStripMenuItem_Click(object sender, EventArgs e) 
    { 

    } 

    private void allDescendantsToolStripMenuItem_Click(object sender, EventArgs e) 
    { 
    } 

    private void contextMenuStrip1_Opening(object sender, CancelEventArgs e) 
    { 
     try 
     { 
      ContextMenuStrip cms = (ContextMenuStrip)sender; 

     } 
     catch 
     { 
     } 
     try 
     { 
      TreeView tv = (TreeView)sender; 
     } 
     catch 
     { 
     } 
    } 

} 
} 

的Program.cs:

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Windows.Forms; 

namespace TestWFA 
{ 
static class Program 
{ 
    /// <summary> 
    /// The main entry point for the application. 
    /// </summary> 
    [STAThread] 
    static void Main() 
    { 
     Application.EnableVisualStyles(); 
     Application.SetCompatibleTextRenderingDefault(false); 
     Application.Run(new Form1()); 
    } 
} 
} 

不幸的是我不知道的任何方式上传文件。我尝试将它们上传为imgs,但没有奏效。

+0

是否上下文菜单中TreeView控件或在TreeView中的每个节点设置? – 2011-06-12 20:09:39

+0

我相信它是为treeView设置的。从那里你可以得到selectedNode。 – user420667 2011-06-12 23:25:12

回答

2

假设您将ContextMenuStrip设置为TreeView。你可以很容易地获得其菜单是从Opened处理程序触发您ContextMenuStrip控制:

private void contextMenuStrip1_Opened(object sender, EventArgs e) 
{ 
    TreeView tv = (sender as ContextMenuStrip).SourceControl as TreeView; 
    tv.Nodes.Add("Tree event catched!"); 
} 

如果的ContextMenuStrip被设置为TreeView的项目这段代码也将工作。

PS:在真正的应用程序中,您不应该使用像(sender as ContextMenuStrip).SourceControl as TreeView;这样的构造,因为可能存在空指针。您应该在每次投射后检查为空。

[编辑]
好的,现在我明白你的目标了。
当您处理菜单项sender对象指向项目触发的事件。要找出弹出上下文菜单的控件,您应该做三件事:

  1. 查找根项目。它的可能性是,被点击的项目是另一项或更深的项目的子项目。
  2. 从根项目你应该找出的ContextMenuStrip对象
  3. 可以很容易地从的ContextMenuStrip的SourceControl财产找出有趣控制

我写简单的方法做一切工作:

/// <summary> 
/// Gets controls for context menu 
/// </summary> 
/// <param name="Sender">Sender object from menu event handler</param> 
/// <returns></returns> 
private object GetSourceControl(Object Sender) 
{ 
    // ContextMenuStrip sended? 
    if (Sender as ContextMenuStrip != null) 
    { 
    ContextMenuStrip cms = Sender as ContextMenuStrip; 
    return cms.SourceControl; 
    } 

    var item = Sender as ToolStripItem; 

    // move to root item 
    while (item.OwnerItem != null) 
    { 
    item = item.OwnerItem; 
    } 

    // we have root item now, so lets take ContextMenuStrip object 
    var menuObject = item.Owner as ContextMenuStrip; 

    if (menuObject != null) 
    { 
    return menuObject.SourceControl; 
    } 

    return null; 
} 

你可以简单地使用它。例如,我们有菜单项的Click事件处理程序:

private void toolStripMenuItem1_Click(object sender, EventArgs e) 
{ 
    TreeView tv = GetSourceControl(sender) as TreeView; 

    if (tv != null) 
    { 
    tv.Nodes.Add("Tree event catched!"); 
    } 
} 

[EDIT2]
由于原来这个问题很早就discused(SourceControl of ContextMenuStrip is Nothing in ToolStripMenuItem Click?)。当您单击根项目时,SourceControl属性不为null,但如果您单击子项目,它将等于null。所以解决方案是将SourceControl的值存储在稍后使用的地方。我建议在Tag属性中执行此操作。因此,所有的方法将是看起来像:

private void contextMenuStrip1_Opening(object sender, CancelEventArgs e) 
{ 
    contextMenuStrip1.Tag = (sender as ContextMenuStrip).SourceControl; 
} 
.... 

private object GetSourceControl(object Sender) 
{ 
    if (Sender as ContextMenuStrip != null) 
    { 
    return ContextMenuStrip.SourceControl; 
    } 

    var item = Sender as ToolStripItem; 

    // move to root item 
    while (item.OwnerItem != null) 
    { 
    item = item.OwnerItem; 
    } 

    // we have root item now, so lets take ContextMenuStrip object 
    var menuObject = item.Owner as ContextMenuStrip; 

    if (menuObject != null) 
    { 
    return menuObject.Tag; 
    } 

    return null; 
} 

在链接的问题有解决办法了私人领域,但Tag属性是习惯性的,我

+0

谢谢。请参阅问题的更新部分。我的问题是从toolstripmenuitem事件处理程序执行此操作。 – user420667 2011-06-13 14:59:07

+1

@ user420667:我编辑了我的答案。希望这会有所帮助 – 2011-06-13 17:02:08

+0

谢谢。不幸的是,仍然没有得到treeView,因为menuObject的SourceControl属性仍然是空的。 (我不得不修改代码,但只有一点点,以使其构建。) – user420667 2011-06-13 17:23:12