Tried several variations, but I either get a TypeMismatch exception or don’t find a logical way…
I have a variable of type variant (can’t avoid variants in my case).
This variable may hold anything, including a single-dimensional array. I have to write its content to a BinaryStream.
My current code works fine as long as the variant doesn’t hold an array of objects:
dim j As Integer
if bs<>nil then
j=VarType(Value)
bs.WriteInt32 j
Select case j
case 11 'Boolean
bs.WriteBoolean Value
case 9 'Object
if Value isa Point then
bs.WriteInt8 16
bs.WriteDouble Point(Value).X
bs.WriteDouble Point(Value).Y
elseif Value isa Picture then
bs.WriteInt8 21
bs.WritePicture Value
Else
bs.WriteInt8 0
dim ex As new RuntimeException("Object type not yet supported.",-50)
Raise ex
end if
case 5 'Double
bs.WriteDouble Value
(and so on for non-array values. Next, for arrays:)
case 4106 'Array of booleans
dim ac,ai As Integer
dim av() As Boolean
av=Value
ac=av.LastIndex
bs.WriteInt32 ac
for ai=0 to ac
bs.WriteBoolean av(ai)
next
bs.WriteInt8 39 'Marker
case 4098 'Array of integers
dim ac,ai,av() As Integer
av=Value
ac=av.LastIndex
bs.WriteInt32 ac
for ai=0 to ac
bs.WriteInt32 av(ai)
next
bs.WriteInt8 39
But, for an array of objects, I have to know which class of objects it holds so I can save each object accordingly.
VarType doesn’t know about my custom classes, so it’s out. I don’t think introspection is good for that either. “IsA” doesn’t work for an array, since it would return the fact it’s an array. I haven’t found another function.
My current code looks like this (but doesn’t work):
case 4105 'Value contains an array of objects
dim vl() as Variant
vl=Value
if UBound(vl)=-1 then 'Empty. Write “9” to the stream (when read back, “9” will have this meaning)
bs.WriteInt8 9
Else
for each v as Variant in vl
bs.WriteInt8 1 //One more object to write
WriteVariantToStream bs,v //Recursion with only a single object
next
bs.WriteInt8 0 //No more objects to save
end if
This compiles fine, but I get a TypeMismatch exception at “vl=Value”, because vl is an array of variants and Value is an array of MyCustomClass.
I could have code like this:
dim vp() as Point
dim vm() as MyClass
dim vi() as Picture
if UBound(Value)=-1 then
'Empty
else
dim v as Variant=Value(0) 'Now I know the type hold in the array
select case true
case v isa Point
vp=Value
//Save each point
case v isa MyClass
vm=Value
//Save each object
case v isa Picture
ci=Value
//Save each picture
…
But this looks clunky.
I’m missing something obvious or it just must be clunky like that?