HarmonyOS APP开发---“滤镜大师“图像处理App,需要用到这个库
HarmonyOS APP开发—"滤镜大师"图像处理App,需要用到这个库
做一个滤镜 App,高斯模糊、边缘检测、色彩矩阵……这些算法用 ArkTS 跑太慢,必须用 C++ 写。但 NAPI 的样板代码让人头秃——
@ohos/aki一行绑定函数、一行绑定类,让 ArkTS 调 C++ 像调本地方法一样简单。
📦 仓库地址:https://gitcode.com/CPF-ApplicationTPC/aki | 安装:
ohpm install @ohos/aki
写在前面
"滤镜大师"的核心是图像处理算法:高斯模糊、Sobel 边缘检测、色彩变换……这些算法要对每个像素做浮点运算,一张 1080p 图有 200 万像素,用 ArkTS 跑可能要好几秒,用 C++ 跑只需几十毫秒。
所以方案很明确:算法用 C++ 写,UI 用 ArkTS 写,中间用 NAPI 桥接。
但原生的 NAPI 写法极其繁琐——注册一个简单的 add(a, b) 函数,要写 napi_get_cb_info、napi_get_value_int32、napi_create_int32 一堆样板。绑定一个 C++ 类?更是一场噩梦。
AKI(Alpha Kernel Interacting)就是来终结这些样板代码的——极简语法糖,一行绑定函数,一行绑定类。
这篇文章聊什么
- C++ 滤镜算法——用 AKI 暴露给 ArkTS
- 绑定 C++ 类——滤镜引擎封装成对象
- Promise 异步处理——大图处理不阻塞 UI
第一步:依赖配置
源码依赖(推荐):
cd entry/src/main/cpp
git clone https://gitcode.com/CPF-ApplicationTPC/aki.git
CMakeLists.txt:
add_subdirectory(aki)
target_link_libraries(filter PUBLIC aki_jsbind)
第二步:C++ 滤镜算法 + AKI 绑定
先写一个简单的高斯模糊,用 AKI 一行绑定暴露给 ArkTS:
// filter.cpp
#include <aki/jsbind.h>
// 高斯模糊:接收像素数组,返回处理后的数组
JSBIND_FUNCTION(applyGaussianBlur) {
// AKI 自动把 ArkTS 参数转成 C++ 类型
auto pixels = args[0].As<std::vector<uint8_t>>(); // 像素数据
int width = args[1].As<int>();
int height = args[2].As<int>();
int radius = args[3].As<int>();
// C++ 高斯模糊算法(省略实现细节)
std::vector<uint8_t> result = gaussianBlur(pixels, width, height, radius);
return result; // AKI 自动转回 ArkTS
}
// 注册到 ArkTS
JSBIND_ADDON(filter)
ArkTS 侧直接调用:
import { applyGaussianBlur } from 'libfilter.so'
// ArkTS 调 C++,就像调本地函数一样
const blurred = applyGaussianBlur(pixelArray, width, height, 5)
// 渲染 blurred 到 Canvas
对比原生 NAPI:同样的功能,NAPI 要写 30+ 行样板代码,AKI 只要 1 行 JSBIND_FUNCTION。类型转换全自动,不用手写 napi_get_value_xxx。
第三步:绑定 C++ 滤镜引擎类
把多个滤镜封装成一个 C++ 类,用 AKI 绑定:
// FilterEngine 类:支持链式应用多个滤镜
class FilterEngine {
public:
FilterEngine() : width_(0), height_(0) {}
void setImage(std::vector<uint8_t> pixels, int width, int height) {
pixels_ = pixels;
width_ = width;
height_ = height;
}
FilterEngine& applyBlur(int radius) {
pixels_ = gaussianBlur(pixels_, width_, height_, radius);
return *this; // 链式调用
}
FilterEngine& applyGrayscale() {
pixels_ = toGrayscale(pixels_, width_, height_);
return *this;
}
FilterEngine& applyBrightness(float factor) {
pixels_ = adjustBrightness(pixels_, width_, height_, factor);
return *this;
}
std::vector<uint8_t> getResult() { return pixels_; }
private:
std::vector<uint8_t> pixels_;
int width_, height_;
};
// AKI 绑定类:构造函数 + 成员方法
JSBIND_CLASS(FilterEngine) {
JSBIND_CONSTRUCTOR();
JSBIND_METHOD(setImage);
JSBIND_METHOD(applyBlur);
JSBIND_METHOD(applyGrayscale);
JSBIND_METHOD(applyBrightness);
JSBIND_METHOD(getResult);
}
JSBIND_ADDON(filter)
ArkTS 侧链式调用:
import { FilterEngine } from 'libfilter.so'
const engine = new FilterEngine()
engine.setImage(pixelArray, 1920, 1080)
.applyBlur(5) // 高斯模糊
.applyGrayscale() // 转灰度
.applyBrightness(1.2) // 提亮 20%
const result = engine.getResult()
// 渲染 result
第四步:Promise 异步处理
4K 大图处理可能要几百毫秒,用 Promise 避免阻塞 UI:
JSBIND_FUNCTION(processImageAsync) {
aki::Promise promise;
std::thread([promise, args]() mutable {
auto pixels = args[0].As<std::vector<uint8_t>>();
// 耗时处理在子线程跑
auto result = heavyProcess(pixels);
promise.Resolve(result); // 完成后 resolve
}).detach();
return promise; // 返回 Promise 给 ArkTS
}
// ArkTS 侧 await
const result = await processImageAsync(pixelArray)
console.info('处理完成')
为什么"滤镜大师"选了 AKI?
| 维度 | 原生 NAPI | @ohos/aki |
|---|---|---|
| 绑定函数 | 30+ 行样板 | 1 行 JSBIND_FUNCTION |
| 绑定类 | 极其繁琐 | JSBIND_CLASS + JSBIND_METHOD |
| 类型转换 | 手写 napi_get/set | 全自动 |
| Promise | 手写 AsyncWorker | aki::Promise |
| 线程安全 | 手写 ThreadSafeFunction | 内置封装 |
| 代码量 | 100% | ~40% |
总结
"滤镜大师"这个场景里,@ohos/aki 解决了三件事:
- 函数绑定——一行
JSBIND_FUNCTION,C++ 算法直接暴露给 ArkTS - 类绑定——
JSBIND_CLASS绑定滤镜引擎,链式调用无缝衔接 - 异步处理——
aki::Promise子线程跑算法,UI 不卡
如果你也需要在鸿蒙应用里复用 C/C++ 库、做高性能计算、调用底层能力,@ohos/aki 让你告别 NAPI 样板代码,把精力留给算法本身。
更多推荐


所有评论(0)