HarmonyOS鸿蒙Next中如何将C++封装后的对象在ArkTS中传入

发布于 1周前 作者 zlyuanteng 来自 鸿蒙OS

HarmonyOS鸿蒙Next中如何将C++封装后的对象在ArkTS中传入

c++ 类通过 napi_wrap 封装后,在ArkTS中调用该类的方法时,通过 napi_unwrap 解封装后,即可正常使用,但我目前想要实现两个类 A、B 封装后的互调,请问如何将对象传入并进行解析,如:

class A { }
class B { 
public: 
    void doA(A* a); 
} 

主要是如何将传入的参数, 从 napi_value 转换为 object A

3 回复

你是否想问如何实现ArkTS与C/C++的对象传递?

可以参考如下demo

ArkTS类对象传递至NAPI侧; NAPI获取对象属性并输出; NAPI调用对象方法。

// Animals类

class Animals {

  name: string
  age: number

  constructor(name: string, age: number) {
    this.name = name;
    this.age = age;
  }

  add(a: number, b: number): number {
    return a + b;
  }
}

// ArkTS传递对象中
Button("TestObject")
  .onClick(() => {
    let ani:Animals = new Animals('Bob',5)
    testNapi.TestObject(ani)
  })

// NAPI接受对象并处理
static napi_value TestObject(napi_env env, napi_callback_info info) {

  size_t argc = 1;
  napi_value args[1] = {nullptr};
  napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);

  napi_value name, age;
  napi_get_named_property(env, args[0], "name", &name);
  napi_get_named_property(env, args[0], "age", &age);

  size_t itemLength;
  napi_get_value_string_utf8(env, name, nullptr, 0, &itemLength);
  char *str = new char[itemLength + 1];
  napi_get_value_string_utf8(env, name, &str[0], itemLength + 1, &itemLength);
  OH_LOG_INFO(LOG_APP, "name is %{public}s", str);

  uint32_t num;
  napi_get_value_uint32(env, age, &num);
  OH_LOG_INFO(LOG_APP, "age is %{public}d", num);

  napi_value add;
  napi_get_named_property(env, args[0], "add", &add);

  // 创建参数数组
  napi_value arr[2];
  napi_create_int32(env, 10, &arr[0]);
  napi_create_int32(env, 5, &arr[1]);

  napi_value result;
  uint32_t res;
  napi_call_function(env, args[0], add, 2, arr, &result);
  napi_get_value_uint32(env, result, &res);
  OH_LOG_INFO(LOG_APP, "res is %{public}d", res);

  return nullptr;
}

ArkTS侧传递回调方法到NAPI侧; NAPI创建napi_value指针类型的对象作为参数传递到回调方法; ArkTS调用回调方法获取NAPI侧传入的参数并做修改; NAPI侧获取修改后的参数并输出。

static bool Napi_AddPropertyInt32(napi_env env, napi_value obj, const char *key, int32_t value) {

  napi_value key_napi = nullptr;
  napi_status status = napi_create_string_utf8(env, key, NAPI_AUTO_LENGTH, &key_napi);
  napi_value value_napi = nullptr;
  status = napi_create_int32(env, value, &value_napi);
  status = napi_set_property(env, obj, key_napi, value_napi);
  return true;
}

static napi_value CallbackToArkTs(napi_env env, napi_callback_info info) {

  // 获取ArkTS参数
  size_t argc = 1;
  napi_value js_cb = nullptr;
  napi_get_cb_info(env, info, &argc, &js_cb, nullptr, nullptr);

  // native回调到ts层的object
  napi_value argv = nullptr;
  napi_create_object(env, &argv);
  Napi_AddPropertyInt32(env, argv, "type", 1);
  Napi_AddPropertyInt32(env, argv, "index", 2);

  // native回调到ts层
  napi_value result = nullptr;
  napi_call_function(env, NULL, js_cb, 1, &argv, &result);

  // 获取ts修改后的object
  napi_value typeNumber = nullptr;
  napi_get_named_property(env, result, "type", &typeNumber);

  int32_t number;
  napi_get_value_int32(env, typeNumber, &number);
  OH_LOG_INFO(LOG_APP, "修改后type: %{public}d", number);

  // 返回修改后的object
  return result;
}

napi_serializenapi_deserializenapi_delete_serialization_data用于将ArkTS对象转换为native数据、将native数据转为ArkTS对象、删除序列化数据等操作,参考: napi_serialize、napi_deserialize、napi_delete_serialization_data

更多关于HarmonyOS鸿蒙Next中如何将C++封装后的对象在ArkTS中传入的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


在HarmonyOS鸿蒙Next中,若要将C++封装后的对象在ArkTS中传入,可以通过以下步骤实现:

  1. 使用NAPI接口:NAPI(Native API)是鸿蒙提供的一种机制,允许在ArkTS中调用C++代码。你需要通过NAPI将C++对象暴露给ArkTS。

  2. 创建C++类:首先在C++中定义并实现你的类,确保该类可以被NAPI封装。

  3. 封装对象:使用NAPI提供的函数将C++对象封装为一个可以在ArkTS中使用的对象。具体步骤包括:

    • 使用napi_define_class定义ArkTS中的类。
    • 使用napi_wrap将C++对象封装为ArkTS对象。
  4. 暴露对象到ArkTS:通过napi_set_named_propertynapi_define_properties将封装后的对象暴露给ArkTS模块。

  5. 在ArkTS中使用:在ArkTS中导入该模块后,可以直接使用封装后的C++对象。

示例代码片段:

#include <napi.h>

class MyClass {
public:
    MyClass() {}
    void doSomething() {
        // C++逻辑
    }
};

Napi::Object Init(Napi::Env env, Napi::Object exports) {
    Napi::Function func = DefineClass(env, "MyClass", {
        InstanceMethod<&MyClass::doSomething>("doSomething")
    });

    exports.Set("MyClass", func);
    return exports;
}

NODE_API_MODULE(addon, Init)

在ArkTS中使用:

import { MyClass } from './my_module';

let myObj = new MyClass();
myObj.doSomething();

在HarmonyOS鸿蒙Next中,将C++封装后的对象传入ArkTS,可以通过以下步骤实现:

  1. 创建Native接口:使用napiNAPI在C++中定义Native接口,将C++对象封装为napi_value
  2. 注册Native模块:在CMakeLists.txt中配置Native模块,并将其注册到ArkTS运行时。
  3. 在ArkTS中调用:通过import引入Native模块,调用封装好的接口,传入C++对象。

示例代码:

napi_value CreateObject(napi_env env, napi_callback_info info) {
    // 创建并返回C++封装的对象
    return napi_create_object(env);
}
import native from 'libnative.so';
let obj = native.createObject();

确保C++对象和ArkTS之间的数据类型兼容,并正确处理生命周期管理。

回到顶部
AI 助手
你好,我是IT营的 AI 助手
您可以尝试点击下方的快捷入口开启体验!