я следующий код в одной сборке:Как добавить обработчик события, используя отражение, когда у вас нет доступа к типу EventArgs?
namespace MyLibrary
{
class InternalClass
{
public event EventHandler<MyArgs> MyEvent;
public void RaiseMyEvent()
{
MyEvent(this, new MyArgs());
}
}
class MyArgs : EventArgs
{
}
}
и следующий код в другой сборке:
namespace MyApp
{
class Program
{
static void Main()
{
var assembly = Assembly.LoadFrom(@"C:\path\to\MyLibrary.dll");
var types = assembly.GetTypes();
var internalClassType = types.FirstOrDefault(t => t.FullName == "MyLibrary.InternalClass");
var eventInfo = internalClassType.GetEvent("MyEvent");
var internalClass = Activator.CreateInstance(internalClassType);
eventInfo.AddEventHandler(internalClass,
Delegate.CreateDelegate(eventInfo.EventHandlerType, typeof(Program), "MyHandler"));
internalClassType.GetMethod("RaiseMyEvent").Invoke(internalClass, new object[0]);
}
public static void MyHandler(object sender, EventArgs e)
{
}
}
}
Однако, я получаю следующее исключение в Delegate.CreateDelegate
: Невозможно привязать к целевой методе потому что его подпись или прозрачность безопасности несовместимы с прозрачностью типа делегата.
Типы в первой сборке являются внутренними и не могут быть изменены, а также не позволяют доступу к сбору доступа к второму.
Я пытался динамически создать метод с помощью следующего:
namespace MyApp
{
class Program
{
static void Main()
{
var assembly = Assembly.LoadFrom(@"C:\path\to\MyLibrary.dll");
var types = assembly.GetTypes();
var internalClassType = types.FirstOrDefault(t => t.FullName == "MyLibrary.InternalClass");
var myArgsType = types.FirstOrDefault(t => t.FullName == "MyLibrary.MyArgs");
var eventInfo = internalClassType.GetEvent("MyEvent");
var methodInfo = typeof(Program).GetMethod("MyHandler");
var method = new DynamicMethod("MyHandlerImpl", null, new[] { typeof(object), myArgsType });
var generator = method.GetILGenerator();
generator.Emit(OpCodes.Ldarg_0);
generator.Emit(OpCodes.Ldarg_1);
generator.Emit(OpCodes.Call, methodInfo);
generator.Emit(OpCodes.Ret);
var internalClass = Activator.CreateInstance(internalClassType);
eventInfo.AddEventHandler(internalClass, method.CreateDelegate(eventInfo.EventHandlerType));
internalClassType.GetMethod("RaiseMyEvent").Invoke(internalClass, new object[0]);
}
public static void MyHandler(object sender, EventArgs e)
{
}
}
}
Однако, я получаю следующее исключение в MethodBase.Invoke
: Попытка методом 'DynamicClass.MyHandlerImpl (System.Object, MyLibrary.MyArgs)' для доступа к типу «MyLibrary.MyArgs» не удалось.
Есть ли способ обработать событие, когда у меня нет доступа к типу EventArgs?
Я узнал что-то новое. Спасибо! – LunicLynx