顾海波

【需求】适配鸿蒙

... ... @@ -23,7 +23,7 @@ class IProcessingCameraImage implements ProcessingCameraImage {
}
IProcessingCameraImage._() {
final DynamicLibrary convertImageLib = Platform.isAndroid
final DynamicLibrary convertImageLib = Platform.isAndroid || Platform.operatingSystem == "ohos"
? DynamicLibrary.open("libconvertImage.so")
: DynamicLibrary.process();
_convertImageYuv420pToRGB = convertImageLib
... ...
/node_modules
/oh_modules
/.preview
/build
/.cxx
/.test
\ No newline at end of file
... ...
/**
* Use these variables when you tailor your ArkTS code. They must be of the const type.
*/
export const HAR_VERSION = '1.0.0';
export const BUILD_MODE_NAME = 'debug';
export const DEBUG = true;
export const TARGET_NAME = 'default';
/**
* BuildProfile Class is used only for compatibility purposes.
*/
export default class BuildProfile {
static readonly HAR_VERSION = HAR_VERSION;
static readonly BUILD_MODE_NAME = BUILD_MODE_NAME;
static readonly DEBUG = DEBUG;
static readonly TARGET_NAME = TARGET_NAME;
}
\ No newline at end of file
... ...
{
"apiType": "stageMode",
"buildOption": {
"externalNativeOptions": {
"path": "./src/main/cpp/CMakeLists.txt",
"arguments": "",
"cppFlags": "",
}
},
"buildOptionSet": [
{
"name": "release",
"arkOptions": {
"obfuscation": {
"ruleOptions": {
"enable": false,
"files": [
"./obfuscation-rules.txt"
]
},
"consumerFiles": [
"./consumer-rules.txt"
]
}
},
"nativeLib": {
"debugSymbol": {
"strip": true,
"exclude": []
}
}
},
],
"targets": [
{
"name": "default"
},
{
"name": "processing_camera_image"
}
]
}
... ...
import { harTasks } from '@ohos/hvigor-ohos-plugin';
export default {
system: harTasks, /* Built-in plugin of Hvigor. It cannot be modified. */
plugins:[] /* Custom plugin to extend the functionality of Hvigor. */
}
... ...
import ProcessingCameraImagePlugin from './src/main/ets/plugin/ProcessingCameraImagePlugin.ets';
export default ProcessingCameraImagePlugin;
\ No newline at end of file
... ...
# Define project specific obfuscation rules here.
# You can include the obfuscation configuration files in the current module's build-profile.json5.
#
# For more details, see
# https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/source-obfuscation-V5
# Obfuscation options:
# -disable-obfuscation: disable all obfuscations
# -enable-property-obfuscation: obfuscate the property names
# -enable-toplevel-obfuscation: obfuscate the names in the global scope
# -compact: remove unnecessary blank spaces and all line feeds
# -remove-log: remove all console.* statements
# -print-namecache: print the name cache that contains the mapping from the old names to new names
# -apply-namecache: reuse the given cache file
# Keep options:
# -keep-property-name: specifies property names that you want to keep
# -keep-global-name: specifies names that you want to keep in the global scope
-enable-property-obfuscation
-enable-toplevel-obfuscation
-enable-filename-obfuscation
-enable-export-obfuscation
\ No newline at end of file
... ...
{
"name": "processing_camera_image",
"version": "1.0.0",
"description": "Please describe the basic information.",
"main": "Index.ets",
"author": "",
"license": "",
"dependencies": {
"@ohos/flutter_ohos": "file:./libs/flutter_embedding.har",
"libconvertImage.so": "file:./src/main/cpp/types/libconvertImage"
},
"modelVersion": "5.0.1",
"compatibleSdkVersion": "13",
"compatibleSdkType": "HarmonyOS"
}
\ No newline at end of file
... ...
# the minimum version of CMake.
cmake_minimum_required(VERSION 3.5.0)
project(MyApplication2)
set(NATIVERENDER_ROOT_PATH ${CMAKE_CURRENT_SOURCE_DIR})
if(DEFINED PACKAGE_FIND_FILE)
include(${PACKAGE_FIND_FILE})
endif()
include_directories(${NATIVERENDER_ROOT_PATH}
${NATIVERENDER_ROOT_PATH}/include)
add_library(convertImage SHARED napi_init.cpp converter.c)
target_link_libraries(convertImage PUBLIC libace_napi.z.so)
\ No newline at end of file
... ...
//
// Created by thuanpm on 4/22/22.
//
#include <stdio.h>
#include "converter.h"
#include <math.h>
#include <stdlib.h>
#define HEXFF 255
int _clamp(int lower, int higher, int val)
{
if (val < lower)
return 0;
else if (val > higher)
return 255;
else
return val;
}
uint32_t *_rotaion_image_32bit(uint32_t *src, double angle, int width, int height, uint32_t background_color)
{
double rad = (angle * M_PI / 180.0);
double sinVal = sin(rad);
double cosVal = cos(rad);
int new_width = (int)(fabs(sinVal * height) + fabs(cosVal * width));
int new_height = (int)(fabs(sinVal * width) + fabs(cosVal * height));
double w2 = 0.5 * width;
double h2 = 0.5 * height;
double dw2 = 0.5 * new_width;
double dh2 = 0.5 * new_height;
uint32_t *dest = malloc(sizeof(uint32_t) * (new_width * new_height));
for (int i = 0; i < new_height; ++i)
{
for (int j = 0; j < new_width; ++j)
{
int oriX = (int)(w2 + (j - dw2) * cosVal + (i - dh2) * sinVal);
int oriY = (int)(h2 - (j - dw2) * sinVal + (i - dh2) * cosVal);
if (oriX >= 0 && oriX < width && oriY >= 0 && oriY < height)
{
dest[i * new_width + j] = src[oriX + oriY * width];
}
else
{
dest[i * new_width + j] = background_color;
}
}
}
free(src);
return dest;
}
uint8_t *_rotaion_image_8bit(uint8_t *src, double angle, int width, int height, uint8_t background_color)
{
double rad = (angle * M_PI / 180.0);
double sinVal = sin(rad);
double cosVal = cos(rad);
int new_width = (int)(fabs(sinVal * height) + fabs(cosVal * width));
int new_height = (int)(fabs(sinVal * width) + fabs(cosVal * height));
double w2 = 0.5 * width;
double h2 = 0.5 * height;
double dw2 = 0.5 * new_width;
double dh2 = 0.5 * new_height;
uint8_t *dest = malloc(sizeof(uint8_t) * (new_width * new_height));
for (int i = 0; i < new_height; ++i)
{
for (int j = 0; j < new_width; ++j)
{
int oriX = (int)(w2 + (j - dw2) * cosVal + (i - dh2) * sinVal);
int oriY = (int)(h2 - (j - dw2) * sinVal + (i - dh2) * cosVal);
if (oriX >= 0 && oriX < width && oriY >= 0 && oriY < height)
{
dest[i * new_width + j] = src[oriX + oriY * width];
}
else
{
dest[i * new_width + j] = background_color;
}
}
}
free(src);
return dest;
}
void _flip_horizontal_32bit(int width, int height, uint32_t *src)
{
int dw2 = (int)(width / 2);
for (int y = 0; y < height; ++y)
{
int y1 = (y * width);
for (int x = 0; x < dw2; ++x)
{
int x2 = (width - 1 - x);
uint32_t t = src[y1 + x2];
src[y1 + x2] = src[y1 + x];
src[y1 + x] = t;
}
}
}
void _flip_horizontal_8bit(int width, int height, uint8_t *src)
{
int dw2 = (int)(width / 2);
for (int y = 0; y < height; ++y)
{
int y1 = (y * width);
for (int x = 0; x < dw2; ++x)
{
int x2 = (width - 1 - x);
uint8_t t = src[y1 + x2];
src[y1 + x2] = src[y1 + x];
src[y1 + x] = t;
}
}
}
void _flip_vertical_32bit(int width, int height, uint32_t *src)
{
int h2 = (int)(height / 2);
for (int y = 0; y < h2; ++y)
{
int y1 = (y * width);
int y2 = (height - 1 - y) * width;
for (int x = 0; x < width; ++x)
{
uint32_t t = src[y2 + x];
src[y2 + x] = src[y1 + x];
src[y1 + x] = t;
}
}
}
void _flip_vertical_8bit(int width, int height, uint8_t *src)
{
int h2 = (int)(height / 2);
for (int y = 0; y < h2; ++y)
{
int y1 = (y * width);
int y2 = (height - 1 - y) * width;
for (int x = 0; x < width; ++x)
{
uint8_t t = src[y2 + x];
src[y2 + x] = src[y1 + x];
src[y1 + x] = t;
}
}
}
uint32_t *convert_image_yuv420p_to_gray(uint8_t *plane0, int width, int height, double angleRotation, uint32_t background_color, bool flip_vertical, bool flip_horizontal)
{
int x, y;
int yp, index;
uint32_t *src = malloc(sizeof(uint32_t) * (width * height));
for (x = 0; x < width; x++)
{
for (y = 0; y < height; y++)
{
index = y * width + x;
yp = plane0[index];
src[x + y * width] = (HEXFF << 24) | (yp << 16) | (yp << 8) | yp;
}
}
if (flip_horizontal)
{
_flip_horizontal_32bit(width, height, src);
}
if (flip_vertical)
{
_flip_vertical_32bit(width, height, src);
}
if (angleRotation == 0)
{
return src;
}
else
{
return _rotaion_image_32bit(src, angleRotation, width, height, background_color);
}
}
uint8_t *convert_image_yuv420p_to_gray_8bit(uint8_t *plane0, int width, int height, double angleRotation, uint8_t background_color, bool flip_vertical, bool flip_horizontal)
{
int x, y;
int index;
uint8_t yp;
uint8_t *src = malloc(sizeof(uint8_t) * (width * height));
for (x = 0; x < width; x++)
{
for (y = 0; y < height; y++)
{
index = y * width + x;
yp = plane0[index];
src[x + y * width] = yp;
}
}
if (flip_horizontal)
{
_flip_horizontal_8bit(width, height, src);
}
if (flip_vertical)
{
_flip_vertical_8bit(width, height, src);
}
if (angleRotation == 0)
{
return src;
}
else
{
return _rotaion_image_8bit(src, angleRotation, width, height, background_color);
}
}
uint32_t *convert_image_yuv420p_to_rgb(uint8_t *plane0, uint8_t *plane1, uint8_t *plane2, int bytesPerRow, int bytesPerPixel, int width, int height, double angleRotation, uint32_t background_color, bool flip_vertical, bool flip_horizontal)
{
int x, y, uvIndex, index;
int yp, up, vp;
int r, g, b;
int rt, gt, bt;
uint32_t *src = malloc(sizeof(uint32_t) * (width * height));
for (x = 0; x < width; ++x)
{
for (y = 0; y < height; ++y)
{
uvIndex = bytesPerPixel * ((int)floor(x / 2)) + bytesPerRow * ((int)floor(y / 2));
index = y * width + x;
yp = plane0[index];
up = plane1[uvIndex];
vp = plane2[uvIndex];
rt = round(yp + vp * 1436 / 1024 - 179);
gt = round(yp - up * 46549 / 131072 + 44 - vp * 93604 / 131072 + 91);
bt = round(yp + up * 1814 / 1024 - 227);
r = _clamp(0, 255, rt);
g = _clamp(0, 255, gt);
b = _clamp(0, 255, bt);
src[x + y * width] = (HEXFF << 24) | (b << 16) | (g << 8) | r;
}
}
if (flip_horizontal)
{
_flip_horizontal_32bit(width, height, src);
}
if (flip_vertical)
{
_flip_vertical_32bit(width, height, src);
}
if (angleRotation == 0)
{
return src;
}
else
{
return _rotaion_image_32bit(src, angleRotation, width, height, background_color);
}
}
uint32_t *convert_image_nv12_to_rgb(uint8_t *plane0, uint8_t *plane1, int bytesPerRow, int bytesPerPixel, int width, int height, double angleRotation, uint32_t background_color, bool flip_vertical, bool flip_horizontal)
{
int x, y, uvIndex, index;
int yp, up, vp;
int r, g, b;
int rt, gt, bt;
uint32_t *src = malloc(sizeof(uint32_t) * (width * height));
for (x = 0; x < width; ++x)
{
for (y = 0; y < height; ++y)
{
uvIndex = bytesPerPixel * ((int)floor(x / 2)) + bytesPerRow * ((int)floor(y / 2));
index = y * width + x;
yp = plane0[index];
up = plane1[uvIndex];
vp = plane1[uvIndex + 1];
rt = round(yp + vp * 1436 / 1024 - 179);
gt = round(yp - up * 46549 / 131072 + 44 - vp * 93604 / 131072 + 91);
bt = round(yp + up * 1814 / 1024 - 227);
r = _clamp(0, 255, rt);
g = _clamp(0, 255, gt);
b = _clamp(0, 255, bt);
src[x + y * width] = (HEXFF << 24) | (b << 16) | (g << 8) | r;
}
}
if (flip_horizontal)
{
_flip_horizontal_32bit(width, height, src);
}
if (flip_vertical)
{
_flip_vertical_32bit(width, height, src);
}
if (angleRotation == 0)
{
return src;
}
else
{
return _rotaion_image_32bit(src, angleRotation, width, height, background_color);
}
}
\ No newline at end of file
... ...
//
// Created by thuanpm on 4/22/22.
//
#ifndef PROCESSING_CAMERA_IMAGE_CONVERTER_H
#define PROCESSING_CAMERA_IMAGE_CONVERTER_H
#ifdef __cplusplus
extern "C"
{
#endif
#include <stdbool.h>
uint8_t *convert_image_yuv420p_to_gray_8bit(uint8_t *plane0, int width, int height, double angleRotation, uint8_t background_color, bool flip_vertical, bool flip_horizontal);
uint32_t *convert_image_nv12_to_rgb(uint8_t *plane0, uint8_t *plane1, int bytesPerRow, int bytesPerPixel, int width, int height, double angleRotation, uint32_t background_color, bool flip_vertical, bool flip_horizontal);
uint32_t *convert_image_yuv420p_to_gray(uint8_t *plane0, int width, int height, double angleRotation, uint32_t background_color, bool flip_vertical, bool flip_horizontal);
uint32_t *convert_image_yuv420p_to_rgb(uint8_t *plane0, uint8_t *plane1, uint8_t *plane2, int bytesPerRow, int bytesPerPixel, int width, int height, double angleRotation, uint32_t background_color, bool flip_vertical, bool flip_horizontal);
#ifdef __cplusplus
}
#endif
#endif // PROCESSING_CAMERA_IMAGE_CONVERTER_H
\ No newline at end of file
... ...
#include "napi/native_api.h"
static napi_value Add(napi_env env, napi_callback_info info)
{
size_t argc = 2;
napi_value args[2] = {nullptr};
napi_get_cb_info(env, info, &argc, args , nullptr, nullptr);
napi_valuetype valuetype0;
napi_typeof(env, args[0], &valuetype0);
napi_valuetype valuetype1;
napi_typeof(env, args[1], &valuetype1);
double value0;
napi_get_value_double(env, args[0], &value0);
double value1;
napi_get_value_double(env, args[1], &value1);
napi_value sum;
napi_create_double(env, value0 + value1, &sum);
return sum;
}
EXTERN_C_START
static napi_value Init(napi_env env, napi_value exports)
{
napi_property_descriptor desc[] = {
{ "add", nullptr, Add, 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 demoModule = {
.nm_version = 1,
.nm_flags = 0,
.nm_filename = nullptr,
.nm_register_func = Init,
.nm_modname = "entry",
.nm_priv = ((void*)0),
.reserved = { 0 },
};
extern "C" __attribute__((constructor)) void RegisterEntryModule(void)
{
napi_module_register(&demoModule);
}
... ...
export const add: (a: number, b: number) => number;
\ No newline at end of file
... ...
{
"name": "libconvertImage.so",
"types": "./Index.d.ts",
"version": "1.0.0",
"description": "Please describe the basic information."
}
\ No newline at end of file
... ...
import {
FlutterPlugin,
FlutterPluginBinding,
MethodCall,
MethodCallHandler,
MethodChannel,
MethodResult,
} from '@ohos/flutter_ohos';
import common from '@ohos.app.ability.common';
/** ProcessingCameraImagePlugin **/
export default class ProcessingCameraImagePlugin implements FlutterPlugin, MethodCallHandler {
private channel: MethodChannel | null = null;
private context: common.Context | null = null;
constructor(context?: common.Context) {
if (context) {
this.context = context;
}
}
getUniqueClassName(): string {
return "ProcessingCameraImagePlugin"
}
onAttachedToEngine(binding: FlutterPluginBinding): void {
this.channel = new MethodChannel(binding.getBinaryMessenger(), "processing_camera_image");
this.channel.setMethodCallHandler(this)
this.context = binding.getApplicationContext();
// hilog.info(0x0000, 'start', 'MMKVPlugin onAttachedToEngine: %{public}s', this.context);
}
onDetachedFromEngine(binding: FlutterPluginBinding): void {
if (this.channel != null) {
this.channel.setMethodCallHandler(null)
}
}
onMethodCall(call: MethodCall, result: MethodResult): void {
result.notImplemented()
}
}
\ No newline at end of file
... ...
{
"module": {
"name": "processing_camera_image",
"type": "har",
"deviceTypes": [
"phone",
"tablet",
"2in1"
]
}
}
\ No newline at end of file
... ...
... ... @@ -35,6 +35,8 @@ flutter:
pluginClass: ProcessingCameraImagePlugin
ios:
pluginClass: ProcessingCameraImagePlugin
ohos:
pluginClass: ProcessingCameraImagePlugin
# To add assets to your plugin package, add an assets section, like this:
# assets:
... ...