OpenHarmony开发者论坛

标题: Napi external 使用示例 [打印本页]

作者: 深开鸿_苟晶晶    时间: 8 小时前
标题: Napi external 使用示例
[md]## 简介

在处理大量数据时,为了避免在JavaScript和native层之间复制数据的性能开销,可以使用napi\_create\_external直接传递数据指针,并通过napi\_get\_value\_external在需要时访问原始数据。本文以一个简单数组的传递介绍如何使用napi\_create\_external,napi\_get\_value\_external。

## 文档环境

开发环境:Windows 10

DevEco Studio 版本:DevEco Studio 4.1 Release(4.1.0.400)

SDK 版本:API version 11 (4.1.7.5 Release)

开发板型号:DAYU200(RK3568)

OpenHarmony版本:OpenHarmony 5.0.2.51

## 使用示例

1. 接口声明、编译配置、模块注册
   接口声明
   
   ```
   export function createExternalArray(): object
   export function useExternalArray(arg: object): void
   ```
   
   编译配置
   
   ```
   cmake_minimum_required(VERSION 3.4.1)
   project(MyApplication2)
   
   set(NATIVERENDER_ROOT_PATH ${CMAKE_CURRENT_SOURCE_DIR})
   
   include_directories(${NATIVERENDER_ROOT_PATH}
                       ${NATIVERENDER_ROOT_PATH}/include)
   
   add_library(entry SHARED external.cpp)
   target_link_libraries(entry PUBLIC libace_napi.z.so libhilog_ndk.z.so)
   ```
   
   模块注册
   
   ```
   EXTERN_C_START
   static napi_value Init(napi_env env, napi_value exports)
   {
       napi_property_descriptor desc[] = {
           {"createExternalArray", nullptr, CreateExternalArray, nullptr, nullptr, nullptr, napi_default, nullptr},
           {"useExternalArray", nullptr, UseExternalArray, nullptr, nullptr, nullptr, napi_default, nullptr},
       };
       napi_define_properties(env, exports, sizeof(desc) / sizeof(desc[0]), desc);
       return exports;
   }
   EXTERN_C_END
   static napi_module nativeModule = {
       .nm_version = 1,
       .nm_flags = 0,
       .nm_filename = nullptr,
       .nm_register_func = Init,
       .nm_modname = "entry",
       .nm_priv = nullptr,
       .reserved = { 0 },
   };
   extern "C" __attribute__((constructor)) void RegisterObjectWrapModule()
   {
       napi_module_register(&nativeModule);
   }
   ```
2. 创建外部数据、获取外部数据
   
   ```
   // 外部数据的释放回调函数:当通过napi_create_external创建的外部值被垃圾回收时,会被调用以释放与之关联的原生资源。
   void FinalizeCallback(napi_env env, void* data, void* hint)
   {
       // 释放数组资源
       int32_t* cppArray = static_cast<int32_t*>(data);
       delete[] cppArray;
   }
   napi_value CreateExternalArray(napi_env env, napi_callback_info info)
   {
       int32_t* cppArray = new int32_t[5]{1, 2, 3, 4, 5};
       napi_status status;
       napi_value jsArray;
       // 创建一个 JavaScript 数组的外部引用
       status = napi_create_external(env, cppArray, FinalizeCallback, NULL, &jsArray);
       if (status != napi_ok) {
           OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, "ARRAY", "napi_create_external_array fail.");
           return nullptr; // 处理错误
       }
       return jsArray; // 返回 JavaScript 数组
   }
   napi_value UseExternalArray(napi_env env, napi_callback_info info)
   {
       size_t argc = 1;
       napi_value args[1];
       int32_t* cppArraydata;
       napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
       // 获取外部数据
       napi_get_value_external(env, args[0], (void**)&cppArraydata);
       // 使用数组数据
       for (size_t i = 0; i < 5; i++) {
          OH_LOG_Print(LOG_APP, LOG_INFO, LOG_DOMAIN, "ARRAY", "napi_get_value_external array: %{public}d", cppArraydata);
       }
       return nullptr;
   }
   ```
3. ArkTS侧示例代码
   
   ```
   let res = testNapi.createExternalArray();
   testNapi.useExternalArray(res);
   ```
4. 运行后,执行结果如下:
   
   ```
   18922-18922  A00000/ARRAY                   com.examp...lication  I     napi_get_value_external array: 1
   18922-18922  A00000/ARRAY                   com.examp...lication  I     napi_get_value_external array: 2
   18922-18922  A00000/ARRAY                   com.examp...lication  I     napi_get_value_external array: 3
   18922-18922  A00000/ARRAY                   com.examp...lication  I     napi_get_value_external array: 4
   18922-18922  A00000/ARRAY                   com.examp...lication  I     napi_get_value_external array: 5
   ```
   
   总结:这段代码展示了如何创建一个外部数组,将其传递给 JavaScript,并在需要时访问和使用这个数组。通过 `napi_create_external` 创建的外部值允许 JavaScript 层访问和操作 C++ 中的数据,而 `napi_get_value_external` 则用于在 native 层访问这些数据。这种机制使得在 JavaScript 和 native 层之间共享和操作数据变得更加灵活和高效。

[/md]




欢迎光临 OpenHarmony开发者论坛 (https://forums.openharmony.cn/) Powered by Discuz! X3.5