Android Question Create Object Instance of B4A Object Using The Typename

Andrew King

Member
Licensed User
I am trying to find a way to create an instance of any type of object using the typename.

I need to create objects at runtime. I know this is kind of frowned upon but in some cases when writing classes to be used in other projects, this function is needed.

To be used like this:

B4X:
Dim obj as object
obj = CreateInstance("b4a.example.fruit")

This is a very simple example that doesn't make much sense to any application but it demonstrates how it could be used.

Is there a function or existing library that can do this and if not what would be the best way to accomplish this?
 
Last edited:

Daestrum

Expert
Licensed User
Longtime User
Couldn't you just use the JavaObject library?
 
Upvote 0

Andrew King

Member
Licensed User
What I'm trying to do is use reflector to read each objects' fields and values that are stored in a list and then transform the data with a function to say a format like XML, CSV then write it to a file.

Then I want to use another function to read the data from the XML or CSV or however I stored it and it create an instance of each object by passing it the typename in a parameter.

I don't want to use stringutils or any other library. I have a specific need for doing it this way. I've coded this in VB.net with ease but b4x doesnt have a GetType(Type) function or Type as Type. It does however have a reflector and javaObject class. Then the only way is to have a CreateInstance function that you pass the typename in string format to, but it must create the instance of the object in a type not derived from javaobject but as the type specified in the typename string parameter. This is needed because the object will later be used in its typed form.
 
Upvote 0

teddybear

Well-Known Member
Licensed User
I don't want to use stringutils or any other library. I have a specific need for doing it this way. I've coded this in VB.net with ease but b4x doesnt have a GetType(Type) function or Type as Type.
Why do you say that? B4X also has the method GetType(object) to get the type of the Object.
 
Upvote 0

drgottjr

Expert
Licensed User
Longtime User
the problem with b4x's gettype(object) is that it returns a string. i think op wants to capture the object's type (not its stringified representation) and then use it later in some method which uses the type (not a string) as the passed parameter. if i understand what he wants, and i'm not sure i do. i don't understand whether he's looking for an instance of b4a.example.fruit or an instance of "b4a.example.fruit"
 
Upvote 1

aeric

Expert
Licensed User
Longtime User
B4X:
Dim Mango As Fruit
Mango.Initialize
Mango.Name = "Mango"
Mango.Origin = "Thailand"
Log(GetType(Mango))            ' b4a.example.main$_fruit

Dim Durian As TropicalFruit
Durian.Initialize
Durian.Name = "Musang King"
Durian.Origin = "Malaysia"
Log(GetType(Durian))           ' b4a.example.tropicalfruit

Dim afruit As Object
afruit = Durian
If GetType(afruit) = "b4a.example.tropicalfruit" Then
    MsgboxAsync("I love Tropical Fruit", afruit.As(TropicalFruit).Name)
End If

1731392777725.png
 

Attachments

  • Fruit.zip
    14.2 KB · Views: 22
Upvote 0

Andrew King

Member
Licensed User
the problem with b4x's gettype(object) is that it returns a string. i think op wants to capture the object's type (not its stringified representation) and then use it later in some method which uses the type (not a string) as the passed parameter. if i understand what he wants, and i'm not sure i do. i don't understand whether he's looking for an instance of b4a.example.fruit or an instance of "b4a.example.fruit"
Right. I'm wanting to get the type by whatever means and then create a new instance of it at runtime not at compile time. Instance of b4a.example.fruit or whatever type that is passed to the function at runtime not compile time.
 
Upvote 0

Andrew King

Member
Licensed User
B4X:
Dim Mango As Fruit
Mango.Initialize
Mango.Name = "Mango"
Mango.Origin = "Thailand"
Log(GetType(Mango))            ' b4a.example.main$_fruit

Dim Durian As TropicalFruit
Durian.Initialize
Durian.Name = "Musang King"
Durian.Origin = "Malaysia"
Log(GetType(Durian))           ' b4a.example.tropicalfruit

Dim afruit As Object
afruit = Durian
If GetType(afruit) = "b4a.example.tropicalfruit" Then
    MsgboxAsync("I love Tropical Fruit", afruit.As(TropicalFruit).Name)
End If

View attachment 158536
So now I want to create an instance of this tropicalfruit or fruit not at compile time but at runtime.
 
Upvote 0

Andrew King

Member
Licensed User
In vb.net I can:
VB.NET:
Public Class Fruit
    Public Property Name as string
    Public Property Color as string
End Class

Public Class Person
    Public Property FirstName as string
    Public Property LastName as string
End Class

Public Module Main
    Public Function RandomObject() as object
        Dim obj as object

        Dim rand = random.next(0,1)

        Select case rand
            case 0
                CreateInstance(gettype(Fruit))
            case 1
                CreateInstance(gettype(Person))
        End Case
    
        Return obj
    End Function

    Public Function CreateInstance(type as type) as Object
        Dim obj = Activator.CreateInstance(type)
        Return obj
    End Function

End Module

I'm trying to do something exactly like this in b4A. Something like vb.net's activator.createinstance. There is JavaObject.InitializeNewInstance but it returns a JavaObject. How to convert this javaobject into a b4a object? Or what other function can create an instance of a b4a object by providing the type or typeName?
 
Last edited:
Upvote 0

Andrew King

Member
Licensed User
I need to be able to pass the type or typename as a parameter in a function and use that to create an instance of that specified type.
 
Upvote 0

Andrew King

Member
Licensed User
I want to create a class
B4X:
Public Class Fruit
    Public Name as string
    Public Color as string
End Class

Then I want to have one function that gets the type
B4X:
Dim typeName as string = GetType(fruit)

Then I want to have another function I can pass the type to and create an instance
B4X:
Sub CreateInstance(PassedType as string) as object
    Dim obj as object
    'code goes here to cast the object into the passedtype
    return obj
End Sub
 
Upvote 0

aeric

Expert
Licensed User
Longtime User
I want to create a class
B4X:
Public Class Fruit
    Public Name as string
    Public Color as string
End Class

Then I want to have one function that gets the type
B4X:
Dim typeName as string = GetType(fruit)

Then I want to have another function I can pass the type to and create an instance
B4X:
Sub CreateInstance(PassedType as string) as object
    Dim obj as object
    'code goes here to cast the object into the passedtype
    return obj
End Sub
I still not get you.
You have everything already.
When you want to use it, you just need to check the type.
 
Upvote 0

aeric

Expert
Licensed User
Longtime User
In vb.net I can:
VB.NET:
Public Class Fruit
    Public Property Name as string
    Public Property Color as string
End Class

Public Class Person
    Public Property FirstName as string
    Public Property LastName as string
End Class

Public Module Main
    Public Function RandomObject() as object
        Dim obj as object

        Dim rand = random.next(0,1)

        Select case rand
            case 0
                CreateInstance(gettype(Fruit))
            case 1
                CreateInstance(gettype(Person))
        End Case
   
        Return obj
    End Function

    Public Function CreateInstance(type as type) as Object
        Dim obj = Activator.CreateInstance(type)
        Return obj
    End Function

End Module

I'm trying to do something exactly like this in b4A. Something like vb.net's activator.createinstance. There is JavaObject.InitializeNewInstance but it returns a JavaObject. How to convert this javaobject into a b4a object? Or what other function can create an instance of a b4a object by providing the type or typeName?
B4X:
TxtName.Text = "B4X"
ShowTheObject(RandomObject)

B4X:
Sub RandomObject As Object
    Select Rnd(0, 2)
        Case 0
            Return CreateFruit(TxtName.Text, "", "")
        Case Else
            Dim someone As Person
            someone.Initialize
            someone.FirstName = TxtName.Text
            Return someone
    End Select
End Sub

Sub ShowTheObject (obj As Object)
    Select GetType(obj)
        Case "b4a.example.person"
            MsgboxAsync("The person first name is " & obj.As(Person).FirstName, "Person")
        Case "b4a.example.main$_fruit"
            MsgboxAsync("The fruit name is " & obj.As(Fruit).Name, "Fruit")
    End Select
End Sub
 
Upvote 0

Andrew King

Member
Licensed User
I believe the solution is:
B4X:
Public Sub CreateInstance(TypeName As String, Params() As Object) As Object
    Dim jo As JavaObject
    Return jo.InitializeNewInstance(TypeName,Params).As(Object)
End Sub

Thanks to aeric for his examples that led me to the solution. Thank you all for your help and time
 
Upvote 0

aeric

Expert
Licensed User
Longtime User
I believe the solution is:
B4X:
Public Sub CreateInstance(TypeName As String, Params() As Object) As Object
    Dim jo As JavaObject
    Return jo.InitializeNewInstance(TypeName,Params).As(Object)
End Sub

Thanks to aeric for his examples that led me to the solution. Thank you all for your help and time
edit: How do you know the parameters for the constructor? ok, it is possible.
I don't think you need to use JavaObject in this case.
 
Upvote 0
Top