使用扩展方法,让菜单也可以Clone

以前一直使用C#2.0,这次为了开发MongoDB的工具,使用了C#4.0.因为用惯了VB,这个也是C#4的处女作了。

一直知道C#的扩展方法,今天第一次使用。。。。。。

现在在做的工具,是恨传统的桌面工具,在制作中发现上下文菜单项和主菜单项ToolStripMenuItem没有Clone的功能,这样的话,无法实现上下文菜单项和主菜单项的共用。

看了网上的一些例子,无非是做一个继承ToolStripMenuItem的新类,然后Copy属性。我的方法是做扩展方法,思路也差不多:

 1  using System;
 2  using System.Collections.Generic;
 3  using System.Linq;
 4  using System.Text;
 5  using System.Windows.Forms;
 6  using System.Reflection;
 7  using System.ComponentModel;
 8  namespace MagicMongoDBTool.Module
 9 {
10      static  class CloneMeunToolItem
11     {
12          ///   <summary>
13           ///  复制菜单项目
14           ///   </summary>
15           ///   <param name="OrgMenuItem"></param>
16           ///   <returns></returns>
17           public  static ToolStripMenuItem Clone( this ToolStripMenuItem OrgMenuItem)
18         {
19             ToolStripMenuItem CloneMenuItem =  new ToolStripMenuItem();
20              // !!!typeof的参数必须是ToolStripMenuItem的基类!!!如果使用Control则不能取到值!!!
21               /// 感谢CSDN网友beargo在帖子【如何获取事件已定制方法名?】里面的提示,网上的例子没有说明这个问题
22               /// 坑爹啊。。。。。。。。
23              Delegate[] _List = GetObjectEventList(OrgMenuItem,  " EventClick "typeof(ToolStripItem));
24             CloneMenuItem.Click +=  new EventHandler(
25                     (x, y) => { _List[ 0].DynamicInvoke(x,y); }
26             );
27             CloneMenuItem.Text = OrgMenuItem.Text;
28              return CloneMenuItem;
29         }
30 
31          ///   <summary>    
32           ///  获取控件事件  zgke@sina.com qq:116149   
33           ///   </summary>    
34           ///   <param name="p_Control"> 对象 </param>    
35           ///   <param name="p_EventName"> 事件名 EventClick EventDoubleClick  这个需要看control.事件 是哪个类的名字是什么 </param>  
36           ///   <param name="p_EventType"> 如果是WINFROM控件  使用typeof(Control) </param>  
37           ///   <returns> 委托列 </returns>    
38           public  static Delegate[] GetObjectEventList( object p_Object,  string p_EventName, Type p_EventType)
39         {
40             PropertyInfo _PropertyInfo = p_Object.GetType().GetProperty( " Events ", BindingFlags.Instance | BindingFlags.NonPublic);
41              if (_PropertyInfo !=  null)
42             {
43                  object _EventList = _PropertyInfo.GetValue(p_Object,  null);
44                  if (_EventList !=  null && _EventList  is EventHandlerList)
45                 {
46                     EventHandlerList _List = (EventHandlerList)_EventList;
47                     FieldInfo _FieldInfo = p_EventType.GetField(p_EventName, BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.IgnoreCase);
48                      if (_FieldInfo ==  nullreturn  null;
49                     Delegate _ObjectDelegate = _List[_FieldInfo.GetValue(p_Object)];
50                      if (_ObjectDelegate ==  nullreturn  null;
51                      return _ObjectDelegate.GetInvocationList();
52                 }
53             }
54              return  null;
55         }  
56     }
57 }

 只是我想说一下,网络上很多代码,包括CSDN上的很多回答。基本上使用了同样的例子。

不过对于这个例子的解释完全没有。特别是哪个坑爹的如果是WINFROM控件  使用typeof(Control)。如果照着这个写的话,菜单项目是没有办法使用的。

正确的说法是 使用控件的 基类。

 

下面报告一下MongoDB工具的进度:

今天完成了数据3种方法展示的功能

 索引管理功能

 

 

 

转载于:https://www.cnblogs.com/TextEditor/archive/2011/10/14/2212625.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值