基于组件的.NET软件开发(4)
发表于:2007-06-30来源:作者:点击数:
标签:
设计示例用到的组件 创建两个 VB .NET类库工程:DynamicComponent和VBDynamicComponent2,分别创建两个窗体VBForm1和VBForm2(如图6图7所示),前者放在DynamicComponent工程中,后者放在VBDynamicComponent2工程中。 分别编译生成两个DLL文件:DynamicCompon
设计示例用到的组件
创建两个
VB.NET类库工程:DynamicComponent和VBDynamicComponent2,分别创建两个窗体VBForm1和VBForm2(如图6图7所示),前者放在DynamicComponent工程中,后者放在VBDynamicComponent2工程中。
分别编译生成两个DLL文件:DynamicComponent.dll和VBDynamicComponent2.dll。
接着,我们创建一个
Windows应用程序VBTestDynamicComponent用于
测试我们的组件装配技术。
读取XML配置文件
在测试程序启动时,它从XML配置文件中读取信息,我们看到,相关信息可以分为两类:一类是要装入的DLL文件清单,另一类是需要装入的类名。这两者是一一对应的,所以,我们可以创建两个ArrayList,一个用于存放文件名,一个用于存放类名,然后,用一个类MyComponentList把这两个ArrayList给封装起来,外部使用者只需给出索引,就可以马上同时得到文件名与类名。
类的接口设计如下:
图 9 用于实现动态装入组件的类
参见图9,只要给MyComponentList类的对象指定一个XML配置文件名,再调用beginRead(),调用者就可以通过索引(0,1,2……)来获取文件名和类名。
读取XML格式数据可以使用.NET framework所提供的XmlTextReader类。完整代码如下:
@#从XML配置文件中读取组件的类名与文件名
Imports System.Collections.Specialized
Imports System.Windows.Forms
Public Class MyComponentList
Private xm
lreader As Xml.XmlTextReader
Private _FileName As String @#XML配置文件名
Private _ComponentFileName As String @#组件库文件名
Private _ComponentName As String @#组件库中的类名
Private componentNames As ArrayList @#存放配置文件中列出的所有组件类名
Private componentFiles As ArrayList @#存放配置文件中列出的所有组件库名
@#在构造函数中创建相关对象
Public Sub New(ByVal FileName As String)
_FileName = FileName
_ComponentFileName = ""
_ComponentName = ""
componentNames = New ArrayList()
componentFiles = New ArrayList()
xmlreader = New Xml.XmlTextReader(FileName)
End Sub
@#XML配置文件名
Public Property FileName() As String
Get
Return _FileName
End Get
Set(ByVal Value As String)
@#文件名空则应抛出异常.
_FileName = Value
End Set
End Property
@#读取组件库
Public Sub beginRead()
Dim b1, b2 As Boolean
b1 = False
b2 = False
@#以下循环读入文件,使用标记b1和b2来实现“组件库文件ß à组件名”的配对,
@#并分别存入对应的两个ArrayList中(componentFiles ß àcomponentNames)
While xmlreader.Read
If xmlreader.Name = "Component" Then
xmlreader.MoveToFirstAttribute()
If xmlreader.Name = "ComponentName" Then
_ComponentName = xmlreader.Value
b1 = True
End If
If xmlreader.Name = "ComponentFileName" Then
_ComponentFileName = xmlreader.Value
b2 = True
End If
While xmlreader.MoveToNextAttribute()
If xmlreader.Name = "ComponentName" Then
_ComponentName = xmlreader.Value()
b1 = True
End If
If xmlreader.Name = "ComponentFileName" Then
_ComponentFileName = xmlreader.Value()
b2 = True
End If
If b1 And b2 Then
componentNames.Add(_ComponentName)
componentFiles.Add(_ComponentFileName)
b1 = False
b2 = False
End If
End While
End If
End While
End Sub
@#取出指定索引的文件名(即组件库文件名)
Public Function getfilename(ByVal index As Integer) As String
Return componentFiles.Item(index)
End Function
@#取出指定索引的类名(即组件名)
Public Function getClassName(ByVal index As Integer) As String
Return componentNames.Item(index)
End Function
End Class
这些代码非常清晰,就不多废话了。
动态创建对象
知道了需要装入的组件,下一步就是如何创建对象了,这需要用到System.Reflection中的类。
同样地,我们也设计一个类LoadComponent用于封装创建对象的功能:
图 10 完成创建组件对象的类
这个类的使用非常简单,给定一个DLL文件名,LoadComponentLibrary()函数用于将此DLL装入内存,之后,便可使用LoadClass创建指定类的对象。
现在我们来逐步分析一下这个类。
(1)装入组件库:
首先必须了解,在.NET中把可以复用的组件库称为“Assembly”,一般译为“程序集”(在上文中所提到的组件库,其实就是指程序集),大多数情况下,每个.NET DLL都是一个程序集。而可以复用的类就放在程序集中。为此,要动态根据类的名字来创建对象,就必须首先把程序集装入内存。在.NET中,可以通过反射技术来实现这一点。示例代码如下:
Private myDll As System.Reflection.Assembly
Public Function LoadComponentLibrary(ByVal ComponentFileName As String) As Boolean
@#装入指定的组件代码库
@#成功返回true
Try
myDll = System.Reflection.Assembly.LoadFrom(ComponentFileName)
If myDll Is Nothing Then
MessageBox.Show("Can@#t Load library")
Return False
End If
Catch Errobj As SystemException
MessageBox.Show(Errobj.Message)
Return False
End Try
Return True
End Function
(2)创建对象:
一旦程序集被装入内存,我们就可以根据类名字串来创建对象了,如下所示:
Private obj As Object
Public Function LoadClass(ByVal classname As String) As Object
If myDll Is Nothing Then
Return Nothing
End If
Try
obj = myDll.CreateInstance(classname)
Catch Errobj As SystemException
MessageBox.Show(Errobj.Message)
Return Nothing
End Try
Return obj
End Function
有了LoadComponent类,我们以后要做的事就简单多了。
原文转自:http://www.ltesting.net