Design example used components
Create two VB.NET class library projects: DynamicComponent and VBDynamicComponent2, create two forms VBFORM1 and VBFORM2 (as shown in Figure 6), the former is placed in the DynamComponent project, and the latter is placed in the VBDynamPonent2 project.
Compile two DLL files separately: DynamicComponent.dll and vbdynamiccomponent2.dll.
Then we create a Windows application vbtestdyNamicComponent to test our component assembly technology.
Read the XML configuration file
When the test program is started, it reads information from the XML configuration file. We see, the relevant information can be divided into two categories: one is the list of DLL files to be loaded, and the other is the class name that needs to be loaded. The two correspond, so we can create two ArrayList, a file name, one is used to store the class name, then, use a class MycomponentList to encapsulate these two arraylist, external users Just give the index, you can get the file name and class name immediately.
The interface is designed as follows:
Figure 9 is used to implement a class of dynamic loading assemblies
Referring to Figure 9, just specify an XML configuration file name for the object of the MyComponentList class, then call BeginRead (), the caller can obtain the file name and class name by index (0, 1, 2 ...).
Read XML format data can use the XMLTextReader class provided by .NET Framework. The full code is as follows:
'Read the class name and file name of the component from the XML configuration file
Imports system.collections.specialized
Imports System.Windows.Forms
Public class mycomponentlist
Private XMlReader As Xml.xmlTextReader
Private _filename as string 'XML configuration file name
Private _componentfilename as string 'component library text name
Private _componentname as string 'class name in the component library
Private ComponentNames as an arraylist 'Store all the component names listed in the configuration file
Private ComponentFiles as arraylist 'storage list listed in the configuration file
'Creating a related object in the constructor
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 configuration file name
Public property filename () AS STRING
Get
Return_filename
END GET
Set (byval value as string)
'File names should throw an exception.
_Filename = value
End set
End Property
'Read the component library
Public Sub Beginread ()
DIM B1, B2 AS BOOLEAN
B1 = FALSE
B2 = false
'The following loop read files, use tags B1 and B2 to implement the pairing of "Component Library Files ßà",
'And deposit into the corresponding two ArrayList (ComponentFiles ß àcomponentnames)
While XmlReader.Read
IF XmlReader.name = "Component" THEN
XmlReader.movetofirsttattribute ()
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.movetonextAtttribute ()
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
'Remove the file name of the specified index (ie the component library file name)
Public Function GetFileName (Byval Index As Integer) AS String
Return ComponentFiles.Item (INDEX)
END FUNCTION
'Take out the class name of the specified index (ie, the component name)
Public Function GetClassName (Byval Index As Integer) AS STRING
Return ComponentNames.Item (Index)
END FUNCTION
END CLASS
These codes are very clear, there is not much nonsense.
Dynamically create objects
I know that the components that need to be loaded, the next step is how to create an object, which requires the class in System.Reflection.
Similarly, we also design a class loadComponent to encapsulate the function of creating an object:
Figure 10 Complete the class of creating component objects
This class is very simple, given a DLL file name, the loadComponentlibrary () function is used to load this DLL into the memory, and then use loadClass to create a specified class object.
Now let's gradually analyze this class.
(1) Load the component library:
First, we must understand that in .NET, the component library that can be multiplexed is called "assembly", which is generally translated into "assembly" (the component library mentioned above, is actually the assembly), most cases Each .NET DLL is an assembly. The class that can be multiplexed is placed in the assembly. To this end, you must create an object based on the name of the class, you must first install the program into memory first. In .NET, this can be achieved by reflection techniques. The sample code is as follows: private mydll as system.reflection.assembly
Public Function Loadcomponentlibrary (Byval ComponentFileName As String) AS Boolean
'Load the specified component code library
'Successfully returned 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) Create an object:
Once the assembly is loaded into memory, we can create an object according to the class name string, as shown below:
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
With the loadcomponent class, what we have to do will be more simply.