鸿蒙NEXT版实战开发:如何在Native侧调用ArkTS侧异步方法,并获取异步计算结果到Native侧?
该场景诉求可以通过在Native侧获取ArkTS侧Promise对象来实现。
·
往期鸿蒙全套实战文章必看:(附带鸿蒙全栈学习资料)
如何在Native侧调用ArkTS侧异步方法,并获取异步计算结果到Native侧
该场景诉求可以通过在Native侧获取ArkTS侧Promise对象来实现。具体步骤如下:
- ArkTS侧实现:
- 调用Native接口时,传入callback回调。在该回调中通过构造函数创建Promise对象;
- 在Promise构造函数的参数回调中,实现异步操作,并根据操作结果,调用resolve或者reject接口,用以对Promise对象进行状态迁移。
- Native侧实现:
- 定义Promise对象then属性的回调方法,用以处理ArkTS侧异步计算结果;
- 定义Promise对象catch属性的回调方法,用以处理ArkTS侧异步计算异常信息;
- 在Native接口实现中,通过napi_call_function接口执行ArkTS侧传入的callback回调,获取Promise对象;
- 通过napi_get_named_property接口获取Promise对象中的then和catch属性;
- 通过napi_create_function接口将上述定义的then和catch属性C++回调方法转换为ArkTS函数对象;
- 通过napi_call_function接口执行then和catch属性对应ArkTS函数对象,用以处理ArkTS侧的异步计算结果和异常信息。类似于在ArkTS侧调用promise.then(()=>{}和promise.catch(()=>{}。
具体可参考以下示例代码:
(一)ArkTS侧实现
// ...
import testNapi from 'libentry.so';
@Entry
@Component
struct Index {
build() {
Row() {
Column() {
Text('testPromise')
// ...
.onClick(() => {
hilog.info(0x0000, 'testTag-ArkTS', 'Before calling the native interface.');
// 调用Native接口,返回调用信息
testNapi.testPromise(() => {
// callback回调用于创建ArkTS侧Promise对象
return new Promise((resolve: Function, reject: Function) => {
// 通过setTimeout接口模拟ArkTS侧异步方法
// 场景:2秒后,触发setTimeout定时器回调,生产一个随机数randomNumber,通过判断随机数的大小,用于触发promise对象不同状态,继而进行不同回调处理
setTimeout(()=>{
const randomNumber: number = 100 * Math.random();
if (randomNumber > 50) {
// 如果randomNumber大于50,则调用resolve方法,将Promise对象的状态转移到fulfilled状态,并将随机数传递到Native侧,作为then方法的回调参数
resolve(randomNumber);
} else {
// 如果randomNumber小于/等于50,则调用reject方法,将Promise对象的状态转移到rejected状态,并将异常信息传递到Native侧,作为catch方法的回调参数
reject('The random number is less than 50, so the promise object is rejected.')
}
}, 2000);
})
}
)
hilog.info(0x0000, 'testTag-ArkTS', 'After the native interface is called.');
})
}
.width('100%')
}
.height('100%')
}
}
(二)Native侧实现
#include "napi/native_api.h"
#include "hilog/log.h"
// 定义Promise对象then属性的回调方法
// then属性的回调方法可以无返回值
// 后文需要通过napi_create_function创建ArkTS函数对象,所以设置返回值为napi_value,并在函数末尾返回nullptr
napi_value ThenCallBack(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);
int32_t asyncResult = 0; // ArkTS侧异步方法计算结果
napi_get_value_int32(env, args[0], &asyncResult);
OH_LOG_Print(LOG_APP, LOG_INFO, 0xFF00, "testTag-Native", "ArkTS Async Method Calculation Success, Result: %{public}d",
asyncResult);
return nullptr;
}
// 定义Promise对象catch属性的回调方法
// catch属性的回调方法可以无返回值
// 后文需要通过napi_create_function创建ArkTS函数对象,所以设置返回值为napi_value,并在函数末尾返回nullptr
napi_value CatchCallBack(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);
size_t strLen = 0;
napi_get_value_string_utf8(env, args[0], nullptr, 0, &strLen); // 获取字符串长度到strLen
char *strBuffer = new char[strLen + 1]; // 分配合适大小的char数组
napi_get_value_string_utf8(env, args[0], strBuffer, strLen + 1, &strLen); // 获取字符串,表示ArkTS侧异步方法计算异常的信息
OH_LOG_Print(LOG_APP, LOG_INFO, 0xFF00, "testTag-Native",
"ArkTS Async Method Calculation Exception: %{public}s", strBuffer);
return nullptr;
}
static napi_value TestPromise(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); // 解析ArkTS侧传入的回调callback
napi_value arktsPromise = nullptr;
// 通过napi_call_function执行callback,返回ArkTS侧创建的promise对象
napi_call_function(env, nullptr, args[0], 0, nullptr, &arktsPromise);
// 获取promise对象的then属性,该属性的回调方法用于处理ArkTS侧异步计算结果
napi_value thenProperty = nullptr;
napi_get_named_property(env, arktsPromise, "then", &thenProperty);
// 将C++语言定义的then属性回调方法转换为ArkTS函数对象,即napi_value类型值
napi_value thenCallback = nullptr;
napi_create_function(env, "thenCallback", NAPI_AUTO_LENGTH, ThenCallBack, nullptr, &thenCallback);
// 获取promise对象的catch属性,该属性的回调方法用于处理ArkTS侧异步计算异常的信息
napi_value catchProperty = nullptr;
napi_get_named_property(env, arktsPromise, "catch", &catchProperty);
// 将C++语言定义的catch属性回调方法转换为ArkTS函数对象,即napi_value类型值
napi_value catchCallback = nullptr;
napi_create_function(env, "catchCallback", NAPI_AUTO_LENGTH, CatchCallBack, nullptr, &catchCallback);
// 通过napi_call_function执行then属性的回调,类似于ArkTS侧调用promise.then(()=>{})
napi_call_function(env, arktsPromise, thenProperty, 1, &thenCallback, nullptr);
// 通过napi_call_function执行catch属性的回调,类似于ArkTS侧调用promise.catch(()=>{})
napi_call_function(env, arktsPromise, catchProperty, 1, &catchCallback, nullptr);
return nullptr;
}
运行结果

- 结果(1):表示ArkTS侧调用Native接口后,Native侧运行并未阻塞,直接返回。
- 结果(2):表示ArkTS侧调用Native接口后,等待2秒(异步计算),因为异步操作中生产的随机数小于等于50,所以通过Promise对象的reject接口传入异常信息到Native侧,并通过catch回调进行显示处理。
- 结果(3):表示ArkTS侧调用Native接口后,等待2秒(异步计算),因为异步操作中生产的随机数大于50,所以通过Promise对象的resolve接口传入随机数到Native侧,并通过then回调进行显示处理。
更多推荐
所有评论(0)