B4J Code Snippet [B4X] Variable # and Named Arguments in Subs

Many of you know how to do this. In the past I have used a variety of techniques, and finally decided on
one method that feels natural to me, and that remains true to the spirit of B4X.

B4X:
'In Globals: Type namedPar(name As String, value As Object)
Private Sub B4XPage_Created (Root1 As B4XView)
    Root = Root1
    testPar(Array(1, 2, True, "ABC", ARG("temperature", 75)))
End Sub

Private Sub testPar(a() As Object)
    Dim pars As B4XOrderedMap = parsePars(a)
    Dim npars As Int = pars.Get(0)        'number of parameters is saved in map at 0
    
    'To iterate through all parameters
    For i = 1 To npars
        Log(i & TAB & pars.Get(i))
    Next
'    1    1
'    2    2
'    3    True
'    4    ABC
'    5    75

    'To retieve the value of the third parameter
    Log(pars.Get(3))        '    True

    'To retieve the value of the fifth parameter
    Log(pars.Get(5))        '    75
    
    'To retrieve the value of a named parameter
    Log(pars.Get("temperature"))        'in this case, it is the same as pars.Get(5) => 75
    
    'To get the name of the 5th parameter
    Log(pars.Keys.Get(pars.Keys.IndexOf(5) + 1))    '    temperature
End Sub

B4X:
#Region Utilities
Private Sub parsePars(a() As Object) As B4XOrderedMap
    Dim m As B4XOrderedMap
    m.Initialize
    For i = 1 To a.Length
        If a(i - 1) Is NamedPar Then
            Dim NPx As NamedPar = a(i - 1)
            m.Put(i, NPx.value)
            m.Put(NPx.name, NPx.Value)
        Else
            m.Put(i, a(i - 1))
        End If
    Next
    m.Put(0, a.Length)
    Return m
End Sub

Public Sub ARG(name As String, value As Object) As NamedPar
    Dim t1 As NamedPar
    t1.Initialize
    t1.name = name
    t1.value = value
    Return t1
End Sub
#End Region
 

William Lancee

Well-Known Member
Licensed User
Longtime User
As soon as you do this, you'll find you need a way to get the type of the passed argument'
There are various ways. Here's mine. Works for most types in B4j and B4a.
Views are inside {}. Structures are inside []. Arrays are explicitly named.

B4X:
Private Sub B4XPage_Created (Root1 As B4XView)
    Root = Root1
    Dim aList As List:   aList.Initialize
    Dim aMap As B4XOrderedMap:  aMap.Initialize
    Dim lbl As Label:  lbl.Initialize("")
    Dim c As B4XView = lbl
    Dim d As B4XView = xui.CreatePanel("")

    testPar(Array(1, 2, True, "ABC", ARG("temperature", 75), _
    d, lbl, c, aMap, aList, _
    Array As Int(7, 8, 9), Array As String("A", "B"), Array As Boolean(True, False), Array As Byte(-100, 100)))
End Sub

B4X:
Private Sub testPar(a() As Object)
    Dim pars As B4XOrderedMap = parsePars(a)
    Dim npars As Int = pars.Get(0)        'number of parameters is saved in map at 0
    
    'To iterate through all parameters
    For i = 1 To npars
        Dim value As Object = pars.Get(i)
        Dim typ As String = vType(value)
        If typ.EndsWith("Array") Or typ.startsWith("[") Or typ.startsWith("{") Then
            Log(i & TAB & "-" & TAB & typ)
        Else
            Log(i & TAB & value & TAB & typ)
        End If
    Next
'    1    1    Integer
'    2    2    Integer
'    3    True    Boolean
'    4    ABC    String
'    5    75    Integer
'    6    -    {B4XView Panel}
'    7    -    {Label}
'    8    -    {Label}
'    9    -    [b4xorderedmap]
'    10    -    [List]
'    11    -    Integer Array
'    12    -    String Array
'    13    -    Boolean Array
'    14    -    Byte Array
End Sub

B4X:
Private Sub vType(obj As Object) As String
    Dim xType As String = GetType(obj)
    If "[" = xType.CharAt(xType.Length - 2) Then
        Select xType.SubString(xType.Length - 1)
            Case "I": xType = "Integer Array"
            Case "F": xType = "Float Array"
            Case "D": xType = "Double Array"
            Case "Z": xType = "Boolean Array"
            Case "B": xType = "Byte Array"
            Case Else
                Log(xType)
        End Select
    Else if xType.contains("String;") Then
        xType = "String Array"
    Else if xType.contains("b4x") Then
        xType = "[" & xType.SubString(xType.LastIndexOf("b4x")) & "]"
    Else
        Dim isView As Boolean = (xType.Contains("widget") Or xType.Contains("scene") Or xType.Contains("layout"))
        If xType.Contains("BALayout") Or xType.Contains("Wrapper") Then
            xType = "B4XView Panel"
            isView = True
        Else
            xType = xType.SubString(xType.LastIndexOf(".") + 1)
        End If
        If isView Then xType = "{" & xType & "}"
        Select True
            Case xType = "ArrayList": xType = "[List]"
            Case xType = "Map$MyMap": xType = "[Map]"
        End Select
    End If
    Return xType
End Sub
 
Top