繁体   English   中英

如何获取控件的处理程序方法以处理另一个控件的相同事件

[英]How to get handler methods of a control to handle the same events of another control

我想找出哪些方法已分配给处理一个控件的事件(从外部),然后分配相同的方法来处理另一个控件的相同事件。 我尝试了以下方法,但没有成功:

private void ReflectMethods(Control control, Control baseControl, string[] excludedEventNames = null, string[] includedEventNames = null)
{
    Type baseType = baseControl.GetType();
    Type ownType = control.GetType();

    foreach (EventInfo baseEventInfo in baseType.GetEvents())
    {
        if (excludedEventNames != null && excludedEventNames.Contains(baseEventInfo.Name))
            continue;

        if (includedEventNames != null && !includedEventNames.Contains(baseEventInfo.Name))
            continue;

        //
        // Checking if current control has the same event..
        //
        foreach (EventInfo ownEventInfo in ownType.GetEvents())
        {
            if (ownEventInfo.Name == baseEventInfo.Name)
            {
                FieldInfo eventField = baseType.GetField(baseEventInfo.Name, BindingFlags.GetField | BindingFlags.NonPublic | BindingFlags.Instance);

                // The above line always returns null, so I cannot get the handler ???
                EventHandler eventHandler = (EventHandler)eventField.GetValue(baseControl);

                ownEventInfo.AddEventHandler(this, eventHandler);
            }
        }
    }
}

只要您使用的控件是由您实现的,您的解决方案就是好的。 发生这种情况是因为编译器会为您可以访问的每个事件创建一个字段,就像发布的代码一样。 但这不是您唯一的方法。 就像属性一样:每个属性通常都有一个字段,但这并不是唯一的方法。

对于Control,要获取与事件关联的委托,您必须通过Events属性获取EventHandlerList,然后使用由字符串“ Event”组成的名称的字段的值来获取访问它的正确EventHandler根据事件的实际名称(例如,对于Click,您必须查找“ EventClick”字段)。

在这里,您可以找到适用于WinForm控件的代码的修改版本。 请注意,它不适用于您自己设计的控件。 您应该结合使用两种方法来管理所有情况。

    private void ReflectMethods(Control control, Control baseControl, string[] excludedEventNames = null, string[] includedEventNames = null)
    {
        Type baseType = baseControl.GetType();
        Type ownType = control.GetType();

        EventHandlerList events = typeof(Control).GetProperty("Events", BindingFlags.Instance | BindingFlags.Public | BindingFlags.Static | BindingFlags.NonPublic).GetValue(baseControl, null) as EventHandlerList;
        foreach (EventInfo baseEventInfo in baseType.GetEvents())
        {
            if (excludedEventNames != null && excludedEventNames.Contains(baseEventInfo.Name))
                continue;

            if (includedEventNames != null && !includedEventNames.Contains(baseEventInfo.Name))
                continue;

            //
            // Checking if current control has the same event..
            //
            foreach (EventInfo ownEventInfo in ownType.GetEvents())
            {
                if (ownEventInfo.Name == baseEventInfo.Name)
                {
                    object eventField = typeof(Control).GetField("Event" + baseEventInfo.Name, BindingFlags.NonPublic | BindingFlags.Static).GetValue(baseControl);
                    Delegate aDel = events[eventField];
                    ownEventInfo.AddEventHandler(control, aDel);
                }
            }
        }
    }

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM