Вам следует запросить определения interface
для свойств, реализующих HasControl
attribute
.
. Для этого вы получите interfaces
, реализованный экземпляром объекта, который используется в форме.
Процедура построения формы может выглядеть следующим образом.
Sub buildForm(model As IModelBase)
Dim interfaceTypes As Type() = model.GetType().FindInterfaces(New TypeFilter(Function(t, c) True), Nothing)
For Each interfaceType As Type In interfaceTypes
Dim properties As PropertyInfo() = interfaceType.GetProperties()
For Each prop As PropertyInfo In properties
Dim attributes As IEnumerable(Of HasControlAttribute) = prop.GetCustomAttributes(Of HasControlAttribute)()
For Each attribute As HasControlAttribute In attributes
Console.Write(attribute.Name)
Console.Write(": ")
Console.WriteLine(CStr(prop.GetValue(model, Nothing)))
' Build label and control here ...
Next
Next
Next
End Sub
Вы также можете получить эти interfaces
из параметра универсального типа (в вашей форме Model
).
Dim interfaceTypes As Type() = GetType(Model).FindInterfaces(New TypeFilter(Function(t, c) True), Nothing)
Вызовите его, передав ему экземпляр объекта, используемый в вашей форме, например.Worker
экземпляр.
Dim worker As Worker = New Worker()
worker.FirstName = "John"
worker.LastName = "Doe"
worker.City = "Brussels"
worker.Age = 40
buildForm(worker)
, что приводит к рассмотрению только отмеченных свойств.
Обратите внимание, что свойство Age
(как пример, определенный для Worker
, не отображается.
First name: John
Last name: Doe
City: Brussels
IModelBase
Public Interface IModelBase
' ...
End Interface
HasControlAttribute
Public Class HasControlAttribute
Inherits Attribute
Public Sub New(ByVal name As String)
Me.Name = name
End Sub
Public Property Name As String
End Class
IHumanData
Public Interface IHumanData
Inherits IModelBase
<HasControl("First name")>
Property FirstName As String
<HasControl("Last name")>
Property LastName As String
'...
End Interface
ILocationData
Public Interface ILocationData
<HasControl("City")>
Property City As String
' ...
End Interface
ISortOfRandomData
Public Interface ISortOfRandomData
'...
End Interface
Рабочий
Public Class Worker
Implements IHumanData, ILocationData
Public Property FirstName As String Implements IHumanData.FirstName
Public Property LastName As String Implements IHumanData.LastName
Public Property City As String Implements ILocationData.City
Public Property Age As Integer
' ...
End Class
ОБНОВЛЕНИЕ
В соответствии с вашим комментарием.
Если вы хотите включить свойства, определенные всам класс Worker
(который не определен ни в одном из реализованных интерфейсов), как показано ниже, тогда массив interfaceTypes
должен включать Type
самого экземпляра объекта.
Dim interfaceTypes As IList(Of Type) = model.GetType().FindInterfaces(New TypeFilter(Function(t, c) True), Nothing).ToList()
interfaceTypes.Add(model.GetType)
Рабочий со свойством Age
, помеченный HasControl
Public Class Worker
Implements IHumanData, ILocationData
Public Property FirstName As String Implements IHumanData.FirstName
Public Property LastName As String Implements IHumanData.LastName
Public Property City As String Implements ILocationData.City
<HasControl("Age")>
Public Property Age As Integer
' ...
End Class