如何访问控件的事件? [英] How to access control's event?

查看:188
本文介绍了如何访问控件的事件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想获得分配给控制
对于如事件的名称:我有两种形式的 A 表b 包含的 gridControl 并gridcontrol有像一些事件的 gridControl1_Validating

I am trying to get the name of the events that is assigned to control For eg: I have two forms A and B .Form B contains GridControl and gridcontrol has some events like gridControl1_Validating.

我的目标仅仅是知道什么是分配给控制

my goal is just to know what are the events assigned to the control

我的代码如下:
FORM A

 public Control[] FilterControls(Control start, Func<Control, bool> isMatch)
    {
        var matches = new List<Control>();
        Action<Control> filter = null;
        (filter = new Action<Control>(c =>
        {
            if (isMatch(c))
                matches.Add(c);
            foreach (Control c2 in c.Controls)
                filter(c2);
        }))(start);

        return matches.ToArray();


    }


     static void main[]
     {


        Control[] FoundControls = null;
        FoundControls = FilterControls(TF, c => c.Name != null && c.Name.StartsWith("grid"));

        var eventinfo = FoundControls[0].GetType().GetEvent("gridControl1.Validating", BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);

     }

在编译我得到我的控制,但我在得到空 eventinfo
虽然gridcontrol事件在 b型

ON compiling I get my control but I am getting null at eventinfo Although gridcontrol event has this event in form B

请帮忙

推荐答案

尝试验证而不是gridControl1.Validating

var eventinfo = FoundControls[0].GetType().GetEvent(
    "Validating",
    BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance);

虽然这有没有关系,你已经附加一个事件处理该事件的事实。你所得到的是事件本身,而不是附加的处理程序,你可以做什么用 eventInfo 变量(其它的添加和删除等事件处理程序)。

Although this have nothing to do with the fact that you have attached an event handler to the event. You are getting the event itself, not the attached handlers. You can do nothing useful with the eventInfo variable (other that adding and removing other event handlers).

要访问附加的处理程序(基本代表),你需要看一下事件的实现代码(使用像反射或的 dotPeek ,或rel=\"nofollow\">微软参考源<使用):

To access attached handlers (underlying delegates) you need to look at the code for the event implementations (using a decompiler like Reflector or dotPeek, or using Microsoft Reference Source):

public event CancelEventHandler Validating
{
    add
    {
        base.Events.AddHandler(EventValidating, value);
    }
    remove
    {
        base.Events.RemoveHandler(EventValidating, value);
    }
}



原来,在控制类使用活动类型的命名属性的 EventHandlerList 存储基础上,所有代表一个的的(<在这种情况下,code> EventValidating 字段)。

It turns out that the Control class uses a property named Events of type EventHandlerList to store all the delegates based on a key (EventValidating field in this case).

要为事件检索的代表,我们应该从<$ C阅读$ C>活动属性:

To retrieve delegates for an event, we should read them from the Events property:

public static Delegate[] RetrieveControlEventHandlers(Control c, string eventName)
{
    Type type = c.GetType();
    FieldInfo eventKeyField = GetStaticNonPublicFieldInfo(type, "Event" + eventName);
    if (eventKeyField == null)
    {
        eventKeyField = GetStaticNonPublicFieldInfo(type, "EVENT_" + eventName.ToUpper());
        if (eventKeyField == null)
        {
            // Not all events in the WinForms controls use this pattern.
            // Other methods can be used to search for the event handlers if required.
            return null;
        }
    }
    object eventKey = eventKeyField.GetValue(c);
    PropertyInfo pi = type.GetProperty("Events",
       BindingFlags.NonPublic | BindingFlags.Instance);
    EventHandlerList list = (EventHandlerList)pi.GetValue(c, null);
    Delegate del = list[eventKey];
    if (del == null)
        return null;
    return del.GetInvocationList();
}

// Also searches up the inheritance hierarchy
private static FieldInfo GetStaticNonPublicFieldInfo(Type type, string name)
{
    FieldInfo fi;
    do
    {
        fi = type.GetField(name, BindingFlags.Static | BindingFlags.NonPublic);
        type = type.BaseType;
    } while (fi == null && type != null);
    return fi;
}

public static List<Delegate> RetrieveAllAttachedEventHandlers(Control c)
{
    List<Delegate> result = new List<Delegate>();
    foreach (EventInfo ei in c.GetType().GetEvents())
    {
        var handlers = RetrieveControlEventHandlers(c, ei.Name);
        if (handlers != null) // Does it have any attached handler?
            result.AddRange(handlers);
    }
    return result;
}



最后一个方法将提取所有连接到控制事件的事件处理程序。这包括所有类处理器(甚至由内部的WinForms附后)。您也可以通过处理程序的目标对象过滤列表:

The last method will extract all the event handlers attached to the control events. This includes handlers from all the classes (even internally attached by winforms). You can also filter the list by the target object of the handler:

public static List<Delegate> RetrieveAllAttachedEventHandlersInObject(Control c, object handlerContainerObject)
{
    return RetrieveAllAttachedEventHandlers(c).Where(d => d.Target == handlerContainerObject).ToList();
}

现在,你可以得到的所有事件处理程序 gridControl1 formB 定义的:

Now you can get all the event handlers of gridControl1 defined in formB:

RetrieveAllAttachedEventHandlersInObject(gridControl1, formB);

这篇关于如何访问控件的事件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆