可以使用按钮单击事件中的以下代码删除事件处理程序。
Button btn = new Button();
this.Controls.Add(btn);
btn.Click += (o, x) =>
{
Button b = o as Button;
FieldInfo eventclick = typeof(Control).GetField("EventClick", BindingFlags.Static | BindingFlags.NonPublic);
object eventValue = eventclick.GetValue(b);
PropertyInfo events = b.GetType().GetProperty("Events", BindingFlags.NonPublic | BindingFlags.Instance);
EventHandlerList eventHandlerList = (EventHandlerList)events.GetValue(b, null);
eventHandlerList .RemoveHandler(eventValue, eventHandlerList [eventValue]);
MessageBox.Show("Test");
};
但我想从vgridcontrols CellValueChanged事件中删除事件处理程序。我需要为以下“EventClick”撰写什么?
FieldInfo eventclick = typeof(Control).GetField(
"EventClick",
BindingFlags.Static | BindingFlags.NonPublic);
答案 0 :(得分:4)
您不能可靠地从事件中删除事件处理程序,除非您已经拥有一个“平等”委托,您可以正常方式使用-=
。
使用反射和黑客攻击字段明显违反了封装和使您的代码非常脆弱。我会强烈建议不要这样做。
“vgridcontrols”(DataGridView
?)你的意思并不清楚,但是你提出的任何解决方案都必然是特定于实现的 - 并且这个实现可以很容易地改变它的下一个版本
相反,花些时间来设计一个你根本不需要删除事件处理程序的设计,或者保持对处理程序的引用并以正常方式删除它。
答案 1 :(得分:0)
这是VB.NET,但您可以轻松地将其修改为C#。这就是你想要的:
'Remove the handler from the cell value changed
Dim gv As DataGridView = Me.equipmentGridView
Dim fInf As FieldInfo = GetType(DataGridView).GetField("EVENT_DATAGRIDVIEWCELLVALUECHANGED", BindingFlags.Static Or BindingFlags.NonPublic)
Dim del As Object = fInf.GetValue(gv)
Dim pInf As PropertyInfo = gv.GetType().GetProperty("Events", BindingFlags.NonPublic Or BindingFlags.Instance)
Dim evList As EventHandlerList = pInf.GetValue(gv, Nothing)
evList.RemoveHandler(del, evList(del))