Ralf Meier Ответов: 1

Создайте делегат из methodinfo


У меня такая ситуация :

Dim myType As Type = Repeat_Tastendruck_Control.GetType
 Dim myInfo As System.Reflection.MethodInfo = myType.GetMethod("OnClick", Reflection.BindingFlags.NonPublic Or Reflection.BindingFlags.Instance)

 If myInfo IsNot Nothing Then
      Dim myDelegate As delegate_OnClick = [Delegate].CreateDelegate(GetType(delegate_OnClick), myInfo, False)
     'Repeat_Tastendruck_Control.Invoke(myDelegate, Nothing)
     myDelegate(EventArgs.Empty)
     Exit Sub
 End If


Я получаю в myType тип Repeat_Tastendruck_Control
Я получаю в myInfo требуемый MethodInfo
Если я сейчас создам делегат для вызова этого метода, он укажет на не созданный экземпляр объекта. Так... где моя ошибка ?
Любое руководство было бы полезно ... ;)

дополнительная информация :

определение OnClick-метода :
Protected Overrides Sub OnClick(e As System.EventArgs)
    MyBase.OnClick(e)
End Sub

определение делегата :
Private Delegate Sub delegate_OnClick(e As EventArgs)


команда " myDelegate(EventArgs. Empty) "вызывает метод right in - но не в элементе управления, на который ссылается"Repeat_Tastendruck_Control".

Что я уже пробовал:

..................................

Richard Deeming

Каково определение OnClick метод, а также delegate_OnClick делегировать?

Ralf Meier

Спасибо за ответ, Ричард. Я обновил/улучшил свой вопрос.

Ralf Meier

Привет Ричард,
Мне очень жаль, но я должен еще раз задать вам этот вопрос.
К вашему сведению: код, который вы мне дали, хорошо работает до сих пор - с одним исключением (и это мой дополнительный вопрос к нему) :

Когда я работаю с элементом управления, где я переопределил метод "OnClick", он работает.
Но когда я работаю с элементом управления, который дает этот метод (я думаю, что он исходит из атрибута Protected-attribute) Я не могу получить делегат - но MethodInfo является правильным и таким же, как MethodInfo из моего производного элемента управления.

Не могли бы вы указать мне еще раз ?..

Richard Deeming

Вероятно, лучше всего опубликовать это как новый вопрос с примером кода, который вы используете.

Ralf Meier

ОК... Я сделаю все, что в моих силах ... ;-)

1 Ответов

Рейтинг:
12

Richard Deeming

Когда вы создаете делегат, указывающий на метод экземпляра, вы должны предоставить "Me"объект, который будет использоваться при вызове делегата. Потому что вы этого не сделали, и вы уточнили False для throwOnBindFailure параметр, для вашего экземпляра делегата будет установлено значение Nothing.

Есть два способа решить эту проблему:

1. Чтобы создать делегат, привязанный к одному экземпляру класса, используйте один из следующих способов: CreateDelegate перегрузки, которые принимают firstArgument параметр:

Dim myDelegate As delegate_OnClick = [Delegate].CreateDelegate(
    GetType(delegate_OnClick),  ' The delegate type
    Repeat_Tastendruck_Control, ' The object instance - "Me"
    myInfo)                     ' The method info

myDelegate(EventArgs.Empty)

Делегат.CreateDelegate Method (Type, Object, MethodInfo) (System)[^]


2. Чтобы создать делегат, который может быть повторно использован с несколькими экземплярами класса, дайте вашему делегату дополнительный параметр для представления экземпляра объекта:
Private Delegate Sub delegate_OnClick(ByVal instance As YourControlType, ByVal e As EventArgs)
...
Dim myDelegate As delegate_OnClick = [Delegate].CreateDelegate(GetType(delegate_OnClick), myInfo, True)

myDelegate(Repeat_Tastendruck_Control, EventArgs.Empty)

NB: Тип первого параметра для делегата должен быть типом, в котором объявлен метод, или производным типом. Если вы хотите передать интерфейс, то MethodInfo должно исходить из интерфейса, а не из класса.


Ralf Meier

Привет Ричард,
Большое спасибо за ваше решение и, конечно же, за объяснение.
Ваше предложение .2 соответствует моему требованию, и я понял это так, как вы объяснили.
Я был совершенно уверен, что не хватает только немного, но я не мог найти его сам.
(все пункты, которые я мог бы вам дать)

раз спасибо
Ральф