1

I have a struct that receives an array of type Float from a C++ library.

class MyStruct extends Struct{      
  @Array.multi([12])
  external Array<Float> states;
}

I am able to receive data and parse it in Dart. Now I want to do the reverse. I have a List<double> which I want to assign to this struct and pass to C++.

The following cast fails at run time.

myStructObject.states = listObject as Array<Float>;

Neither Array class, nor List class has any related methods. Any idea on this?

Brandon DeRosier
  • 861
  • 5
  • 15
Sanjay
  • 315
  • 3
  • 15

1 Answers1

3

There's no way to get around copying elements into FFI arrays.

for (var i = 0; i < listObject.length; i++) {
  my_struct.states[i] = listObject[i];
}

This may seem inefficient, but consider that depending on the specialization of listObject, the underlying memory layout of the data may differ significantly from the contiguous FFI layout, and so a type conversion sugar provided by Dart would likely also need to perform conversions on individual elements anyways (as opposed to just performing a single memcpy under the hood).

One possibility for closing the convenience gap would be to define an extension method. For example:

extension FloatArrayFill<T> on ffi.Array<ffi.Float> {
  void fillFromList(List<T> list) {
    for (var i = 0; i < list.length; i++) {
      this[i] = list[i] as double;
    }
  }
}

Usage:

my_struct.states.fillFromList(list);

Note that a separate extension method would be need to be defined for each ffi.Array<T> specialization you want to do this for (Array<Uint32>, Array<Double>, Array<Bool>, etc.). This is due to the [] operator being implemented through a separate extension method for each of these type specializations internally.

Brandon DeRosier
  • 861
  • 5
  • 15
  • First approach I also had tried. It was giving me error. Second approach of extension method worked. Thank you. – Sanjay Jan 21 '22 at 11:11