0

我正在尝试使用 Dart 包装一个 C 库。我从 dart 调用一个 C 函数,并通过 C 中的 Dart_NativeArguments 结构传入参数:

    void _sayHello(Dart_NativeArguments arguments) {
    string from;
    Dart_Handle seed_object = HandleError(Dart_GetNativeArgument(arguments, 0));
    if (Dart_IsString(seed_object)) {
        const char* seed;
        HandleError(Dart_StringToCString(seed_object, &seed));
        from = seed;
    }
    num = (int)Dart_GetNativeArgument(arguments, 1);

    Dart_SetReturnValue(arguments, HandleError(Dart_NewStringFromCString(sayHello(from, num).c_str())));
}

在 Dart 中,我调用函数并传入必要的参数

String sayHello(String from) native "sayHello";

main() {
  print(sayHello("Dart"));
}

我想知道如何传递指针(指向我创建的结构),而不仅仅是字符串和整数作为参数。Dart 中有一些函数可以将 Dart_Handles 转换为字符串和整数,但不能转换为指针。Dart_Handle 的内部结构是什么,我将如何将其转换回指针?例如:

飞镖代码:

String sayHello(info from) native "sayHello";


class info
{
  String message;
  int num;
}

main() {
  info tester = new info();
  tester.message = "Dart";
  tester.num = 2;
  print(sayHello(tester));
}

C代码:

void sayHello(Dart_NativeArguments arguments) {
    /*What do I do here to get back a pointe to the struct/class I passed
      in as an argument in Dart?*/
}
4

1 回答 1

1

Dart_NativeArguments将只包含一个项目,这将是一个实例info-您使用创建的类的实例new info()。您可以测试它是否是带有bool Dart_IsInstance(Dart_Handle object). 因此,您拥有的是 info 实例的句柄。这允许您访问其实例字段(message 和 num)来获取和设置它们,使用Dart_GetFieldand Dart_SetField

Dart_Handle instance = Dart_GetNativeArgument(arguments, 0);
Dart_Handle message_handle = Dart_GetField(retobj, NewString("message"));
char* message;
Dart_StringToCString(message_handle, &message);
Dart_Handle number_handle = Dart_GetField(retobj, NewString("num"));
int64_t number;
Dart_IntegerToInt64(number_handle, &number);
// message contains the string, number contains the number
// use them, copy them etc

我知道这只是一个示例,但重新定义sayHello采用 2 个参数(一个字符串和一个 int)可能比传递一个对象实例更容易。没有办法一步访问类的字段,您需要单独访问它们。考虑这两个版本的 Dart 代码,一个传递一个对象实例,一个只传递值。第二个版本在 Dart 和 C 端更简单(没有 GetField 步骤)。不过,第一个版本更强大,因为您可以使用 SetField 更新字段,而在第二个版本中则不能。

class Info {
  String message;
  int num;

  Info(this.message, this.num);
}

version1() {
  sayHelloV1(new Info('Dart', 2));
}

version2() {
  sayHelloV2('Dart', 2);
}

如果您的 C API 要求您传入 a struct,则必须通过将使用 etc 提取的值复制到其中来在 C 代码中创建Dart_IntegerToInt64它,然后将指向您的 C 结构的指针传递给 API。

如果您的 API非常精确地将数据打包/填充到结构中,您可以使用 Darttyped_data将 Dart 类型打包到 a 中ByteData并传递底层字节数组。

于 2018-06-11T21:21:13.637 回答