使用变量作为动作动态创建事件句柄
Create Event handles dynamically using variable as the actions
我正在尝试改进我们的动态报告系统。我想将事件句柄添加到我在表单上动态创建的对象。其中一个功能是根据第一个列表框中 selected 的内容填充一个列表框。即用户select一个城镇,第二个列表框由居住在该城镇的所有人填充。
objectaction 和 objectactionfunction 将存储在系统中的 SQL table 中。我还想将 objectactionfunction 代码存储在 table 中并在运行时动态创建它。我一直在研究 CodeDOM。我在寻找正确的方向吗?
下面的伪代码
dim objectaction as string
dim objectactionfunction as string
objectaction = "LostFocus"
objectactionfunction =" "
addHandler textbox1.objectaction, addressof objectactionfunction
下面是一个使用反射注册事件处理程序的例子,使用Strings
指定事件名称和事件处理程序名称:
Imports System.Reflection
Public Class Form1
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
Dim eventName = "Leave"
Dim methodName = "TextBox1_Leave"
Dim targetType = TextBox1.GetType()
Dim [event] = targetType.GetEvent(eventName)
Dim eventHandlerType = [event].EventHandlerType
Dim eventHandlerMethod = Me.GetType().GetMethod(methodName, BindingFlags.NonPublic Or BindingFlags.Instance)
Dim eventHandlerDelegate = eventHandlerMethod.CreateDelegate(eventHandlerType, Me)
[event].AddEventHandler(TextBox1, eventHandlerDelegate)
End Sub
Private Sub TextBox1_Leave(sender As Object, e As EventArgs)
MessageBox.Show("Success!")
End Sub
End Class
正如我在评论中所说,代码相当冗长,但就是这样。这里有一个扩展方法,您可以使用它编写一次代码并在任何地方使用它:
Imports System.Reflection
Imports System.Runtime.CompilerServices
Public Module ObjectExtensions
<Extension>
Public Sub AddEventHandler(source As Object,
eventName As String,
eventHandlerName As String,
eventHandlerSource As Object)
Dim [event] = source.GetType().GetEvent(eventName)
Dim eventHandlerMethod = eventHandlerSource.GetType().GetMethod(eventHandlerName, BindingFlags.NonPublic Or BindingFlags.Instance)
Dim eventHandlerDelegate = eventHandlerMethod.CreateDelegate([event].EventHandlerType, eventHandlerSource)
[event].AddEventHandler(source, eventHandlerDelegate)
End Sub
End Module
示例用法:
Dim eventName = "Leave"
Dim methodName = "TextBox1_Leave"
TextBox1.AddEventHandler(eventName, methodName, Me)
我正在尝试改进我们的动态报告系统。我想将事件句柄添加到我在表单上动态创建的对象。其中一个功能是根据第一个列表框中 selected 的内容填充一个列表框。即用户select一个城镇,第二个列表框由居住在该城镇的所有人填充。
objectaction 和 objectactionfunction 将存储在系统中的 SQL table 中。我还想将 objectactionfunction 代码存储在 table 中并在运行时动态创建它。我一直在研究 CodeDOM。我在寻找正确的方向吗? 下面的伪代码
dim objectaction as string
dim objectactionfunction as string
objectaction = "LostFocus"
objectactionfunction =" "
addHandler textbox1.objectaction, addressof objectactionfunction
下面是一个使用反射注册事件处理程序的例子,使用Strings
指定事件名称和事件处理程序名称:
Imports System.Reflection
Public Class Form1
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
Dim eventName = "Leave"
Dim methodName = "TextBox1_Leave"
Dim targetType = TextBox1.GetType()
Dim [event] = targetType.GetEvent(eventName)
Dim eventHandlerType = [event].EventHandlerType
Dim eventHandlerMethod = Me.GetType().GetMethod(methodName, BindingFlags.NonPublic Or BindingFlags.Instance)
Dim eventHandlerDelegate = eventHandlerMethod.CreateDelegate(eventHandlerType, Me)
[event].AddEventHandler(TextBox1, eventHandlerDelegate)
End Sub
Private Sub TextBox1_Leave(sender As Object, e As EventArgs)
MessageBox.Show("Success!")
End Sub
End Class
正如我在评论中所说,代码相当冗长,但就是这样。这里有一个扩展方法,您可以使用它编写一次代码并在任何地方使用它:
Imports System.Reflection
Imports System.Runtime.CompilerServices
Public Module ObjectExtensions
<Extension>
Public Sub AddEventHandler(source As Object,
eventName As String,
eventHandlerName As String,
eventHandlerSource As Object)
Dim [event] = source.GetType().GetEvent(eventName)
Dim eventHandlerMethod = eventHandlerSource.GetType().GetMethod(eventHandlerName, BindingFlags.NonPublic Or BindingFlags.Instance)
Dim eventHandlerDelegate = eventHandlerMethod.CreateDelegate([event].EventHandlerType, eventHandlerSource)
[event].AddEventHandler(source, eventHandlerDelegate)
End Sub
End Module
示例用法:
Dim eventName = "Leave"
Dim methodName = "TextBox1_Leave"
TextBox1.AddEventHandler(eventName, methodName, Me)