From 65afa78f2ddb723acf851cb9a1277f24c9444c8f Mon Sep 17 00:00:00 2001 From: wangmiaoliang Date: Sat, 25 Jun 2022 19:26:33 +0800 Subject: [PATCH] effectKit.ColorPicker.GetMainColor Signed-off-by: wangmiaoliang Change-Id: Ica9a426d737c56dc8d9c4ca4657dec5f720c7165 --- bundle.json | 1 + interfaces/kits/napi/BUILD.gn | 1 + .../kits/napi/graphic/effect_kit/BUILD.gn | 79 +++ .../effect_kit/include/color_picker_napi.h | 68 +++ .../include/native_module_ohos_effect.h | 22 + .../effect_kit/src/color_picker_napi.cpp | 520 ++++++++++++++++++ .../src/native_module_ohos_effect.cpp | 54 ++ rosen/modules/effect/color_picker/BUILD.gn | 77 +++ .../color_picker/include/color_picker.h | 55 ++ .../color_picker/include/effect_errors.h | 30 + .../effect/color_picker/include/effect_type.h | 31 ++ .../color_picker/include/effect_utils.h | 35 ++ .../effect/color_picker/src/color_picker.cpp | 106 ++++ rosen/modules/effect/test/unittest/BUILD.gn | 29 +- 14 files changed, 1100 insertions(+), 8 deletions(-) create mode 100644 interfaces/kits/napi/graphic/effect_kit/BUILD.gn create mode 100644 interfaces/kits/napi/graphic/effect_kit/include/color_picker_napi.h create mode 100644 interfaces/kits/napi/graphic/effect_kit/include/native_module_ohos_effect.h create mode 100644 interfaces/kits/napi/graphic/effect_kit/src/color_picker_napi.cpp create mode 100644 interfaces/kits/napi/graphic/effect_kit/src/native_module_ohos_effect.cpp create mode 100644 rosen/modules/effect/color_picker/BUILD.gn create mode 100644 rosen/modules/effect/color_picker/include/color_picker.h create mode 100644 rosen/modules/effect/color_picker/include/effect_errors.h create mode 100644 rosen/modules/effect/color_picker/include/effect_type.h create mode 100644 rosen/modules/effect/color_picker/include/effect_utils.h create mode 100644 rosen/modules/effect/color_picker/src/color_picker.cpp diff --git a/bundle.json b/bundle.json index 3ebb198467..21d294f3d4 100755 --- a/bundle.json +++ b/bundle.json @@ -75,6 +75,7 @@ "//foundation/graphic/graphic_2d/rosen/modules/render_service:render_service", "//foundation/graphic/graphic_2d/rosen/modules/render_service:render_service_dump", "//foundation/graphic/graphic_2d/rosen/modules/effect/effectChain:libeffectchain", + "//foundation/graphic/graphic_2d/rosen/modules/effect/color_picker:color_picker", "//foundation/graphic/graphic_2d/frameworks/opengl_wrapper:EGL", "//foundation/graphic/graphic_2d/frameworks/opengl_wrapper:GLESv3", "//foundation/graphic/graphic_2d/frameworks/opengl_wrapper:opengl_wrapper_native_test", diff --git a/interfaces/kits/napi/BUILD.gn b/interfaces/kits/napi/BUILD.gn index 95b92e6505..00464d5f46 100644 --- a/interfaces/kits/napi/BUILD.gn +++ b/interfaces/kits/napi/BUILD.gn @@ -14,6 +14,7 @@ group("napi_packages") { deps = [ "graphic/animation/window_animation_manager:windowanimationmanager_napi", + "graphic/effect_kit:effectkit", "graphic/webgl:libwebglnapi", ] } diff --git a/interfaces/kits/napi/graphic/effect_kit/BUILD.gn b/interfaces/kits/napi/graphic/effect_kit/BUILD.gn new file mode 100644 index 0000000000..0991620a97 --- /dev/null +++ b/interfaces/kits/napi/graphic/effect_kit/BUILD.gn @@ -0,0 +1,79 @@ +# Copyright (c) 2021 Huawei Device Co., Ltd. +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +import("//build/ohos.gni") + +## Build effect_kit.so + +config("graphic_napi_effect_kit_config") { + visibility = [ ":*" ] + + cflags = [ + "-Wall", + "-Werror", + "-g3", + "-Wno-pointer-arith", + "-Wno-non-virtual-dtor", + "-Wno-missing-field-initializers", + "-Wno-c++11-narrowing", + ] + + defines = [ "EGL_EGLEXT_PROTOTYPES" ] +} + +ohos_shared_library("effectkit") { + include_dirs = [ + "./include", + "//foundation/graphic/graphic_2d/rosen/modules/effect/effectChain/include", + "//foundation/graphic/graphic_2d/rosen/modules/effect/egl/include", + "//foundation/graphic/graphic_2d/rosen/modules/effect/color_picker/include", + "//foundation/graphic/graphic_2d/utils/color_manager/export", + "//foundation/multimedia/image_standard/interfaces/kits/js/common/include", + "//foundation/multimedia/image_standard/interfaces/innerkits/include", + "//base/hiviewdfx/hilog/interfaces/native/innerkits/include", + ] + + configs = [ + ":graphic_napi_effect_kit_config", + "//utils/native/base:utils_config", + "//foundation/multimedia/image_standard/interfaces/innerkits:image_external_config", + ] + + sources = [ + "./src/color_picker_napi.cpp", + "./src/native_module_ohos_effect.cpp", + ] + + deps = [ + "//base/hiviewdfx/hilog/interfaces/native/innerkits:libhilog", + "//foundation/arkui/napi:ace_napi", + "//foundation/graphic/graphic_2d:libgl", + "//foundation/graphic/graphic_2d:libsurface", + "//foundation/graphic/graphic_2d/rosen/modules/effect/color_picker:color_picker", + "//foundation/graphic/graphic_2d/rosen/modules/effect/effectChain:libeffectchain", + "//foundation/graphic/graphic_2d/rosen/modules/effect/egl:libegl_effect", + "//foundation/graphic/graphic_2d/utils/color_manager:color_manager", + "//foundation/multimedia/image_standard/interfaces/innerkits:image", + "//foundation/multimedia/image_standard/interfaces/innerkits:image_native", + "//utils/native/base:utils", + ] + + external_deps = [ "hitrace_native:hitrace_meter" ] + + cflags_cc = [ "-std=c++17" ] + + relative_install_dir = "module" + part_name = "graphic_standard" + subsystem_name = "graphic" +} +## Build effect_kit.so diff --git a/interfaces/kits/napi/graphic/effect_kit/include/color_picker_napi.h b/interfaces/kits/napi/graphic/effect_kit/include/color_picker_napi.h new file mode 100644 index 0000000000..e625997ab6 --- /dev/null +++ b/interfaces/kits/napi/graphic/effect_kit/include/color_picker_napi.h @@ -0,0 +1,68 @@ +/* + * Copyright (C) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef COLOR_PICKER_NAPI_H_ +#define COLOR_PICKER_NAPI_H_ + +#include "effect_type.h" +#include "napi/native_api.h" +#include "napi/native_node_api.h" + +namespace OHOS { +namespace Media { +class PixelMap; +} +namespace Rosen { +class ColorPicker; +enum class ImageType { + TYPE_UNKOWN = 100, + TYPE_PIXEL_MAP, + TYPE_IMAGE_SOURCE, +}; + +class ColorPickerNapi { +public: + ColorPickerNapi(); + ~ColorPickerNapi(); + static napi_value Init(napi_env env, napi_value exports); + +private: + // methods constructor + static napi_value Constructor(napi_env env, napi_callback_info info); + static void Destructor(napi_env env, void* nativeObject, void* finalize); + + // static mothod + static napi_value CreateColorPicker(napi_env env, napi_callback_info info); + static void CreateColorPickerFromPixelmapComplete(napi_env env, napi_status status, void *data); + static napi_value GetScaledPixelMap(napi_env env, napi_callback_info info); + static napi_value GetMainColor(napi_env env, napi_callback_info info); + static napi_value GetMainColorSync(napi_env env, napi_callback_info info); + + static ImageType ParserArgumentType(napi_env env, napi_value argv); + + // napi var + napi_env env_ = nullptr; + napi_ref wrapper_ = nullptr; + + // var for create ColorPicker + static thread_local napi_ref sConstructor_; + static std::shared_ptr sColorPicker_; + + // native var + std::shared_ptr nativeColorPicker_; +}; +} // namespace Rosen +} // namespace OHOS +#endif /* COLOR_PICKER_NAPI_H_ */ diff --git a/interfaces/kits/napi/graphic/effect_kit/include/native_module_ohos_effect.h b/interfaces/kits/napi/graphic/effect_kit/include/native_module_ohos_effect.h new file mode 100644 index 0000000000..da791144fd --- /dev/null +++ b/interfaces/kits/napi/graphic/effect_kit/include/native_module_ohos_effect.h @@ -0,0 +1,22 @@ +/* + * Copyright (C) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef NATIVE_MODULE_OHOS_EFFECT_H_ +#define NATIVE_MODULE_OHOS_EFFECT_H_ + +#include "napi/native_node_api.h" +#include "color_picker_napi.h" + +#endif /* NATIVE_MODULE_OHOS_EFFECT_H_ */ diff --git a/interfaces/kits/napi/graphic/effect_kit/src/color_picker_napi.cpp b/interfaces/kits/napi/graphic/effect_kit/src/color_picker_napi.cpp new file mode 100644 index 0000000000..0274b9c5f9 --- /dev/null +++ b/interfaces/kits/napi/graphic/effect_kit/src/color_picker_napi.cpp @@ -0,0 +1,520 @@ +/* + * Copyright (C) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "image_napi_utils.h" +#include "effect_errors.h" +#include "image_napi_utils.h" +#include "color_picker.h" +#include "color.h" +#include "pixel_map_napi.h" +#include "hilog/log.h" +#include "effect_utils.h" +#include "color_picker_napi.h" + +using OHOS::HiviewDFX::HiLog; +namespace { + constexpr uint32_t NUM_0 = 0; + constexpr uint32_t NUM_1 = 1; + constexpr uint32_t NUM_2 = 2; + constexpr uint32_t NUM_4 = 4; +} + +namespace OHOS { +namespace Rosen { +static const std::string CLASS_NAME = "ColorPicker"; +thread_local napi_ref ColorPickerNapi::sConstructor_ = nullptr; +std::shared_ptr ColorPickerNapi::sColorPicker_ = nullptr; + +// context +struct ColorPickerAsyncContext { + napi_env env; + napi_async_work work; + napi_deferred deferred; + napi_ref callbackRef; + uint32_t status; + // build error msg + napi_value errorMsg = nullptr; + ColorPickerNapi *nConstructor; + std::shared_ptr rColorPicker; + std::shared_ptr rPixelMap; + ColorManager::Color color; +}; + +static void BuildMsgOnError(napi_env env, + const std::unique_ptr& context, + bool assertion, + const std::string msg); + +static napi_value BuildJsColor(napi_env env, ColorManager::Color color); + +static void CommonCallbackRoutine(napi_env env, ColorPickerAsyncContext* &asyncContext, const napi_value &valueParam) +{ + napi_value result[NUM_2] = {0}; + napi_value retVal; + napi_value callback = nullptr; + + napi_get_undefined(env, &result[NUM_0]); + napi_get_undefined(env, &result[NUM_1]); + EFFECT_LOG_I("Create ColorPicker Common Callback Routine"); + + if (asyncContext->status == SUCCESS) { + result[NUM_1] = valueParam; + } else if (asyncContext->errorMsg != nullptr) { + result[NUM_0] = asyncContext->errorMsg; + } else { + napi_create_string_utf8(env, "Internal error", NAPI_AUTO_LENGTH, &(result[NUM_0])); + } + + if (asyncContext->deferred) { + if (asyncContext->status == SUCCESS) { + napi_resolve_deferred(env, asyncContext->deferred, result[NUM_1]); + } else { + napi_reject_deferred(env, asyncContext->deferred, result[NUM_0]); + } + } else { + napi_get_reference_value(env, asyncContext->callbackRef, &callback); + napi_call_function(env, nullptr, callback, NUM_2, result, &retVal); + napi_delete_reference(env, asyncContext->callbackRef); + } + + napi_delete_async_work(env, asyncContext->work); + + delete asyncContext; + asyncContext = nullptr; +} + +ColorPickerNapi::ColorPickerNapi() + :env_(nullptr), wrapper_(nullptr) +{ +} + +ColorPickerNapi::~ColorPickerNapi() +{ + if (nativeColorPicker_ != nullptr) { + nativeColorPicker_ = nullptr; + } + + if (wrapper_ != nullptr) { + napi_delete_reference(env_, wrapper_); + } +} + +napi_value ColorPickerNapi::Init(napi_env env, napi_value exports) +{ + napi_property_descriptor props[] = { + DECLARE_NAPI_FUNCTION("getMainColor", GetMainColor), + DECLARE_NAPI_FUNCTION("getMainColorSync", GetMainColorSync), + }; + + napi_property_descriptor static_prop[] = { + DECLARE_NAPI_STATIC_FUNCTION("createColorPicker", CreateColorPicker), + }; + + napi_value constructor = nullptr; + + napi_status status = napi_define_class(env, CLASS_NAME.c_str(), + NAPI_AUTO_LENGTH, Constructor, + nullptr, + IMG_ARRAY_SIZE(props), props, + &constructor); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("define class fail")); + + status = napi_create_reference(env, constructor, 1, &sConstructor_); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("create reference fail")); + + napi_value global = nullptr; + status = napi_get_global(env, &global); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("Init:get global fail")); + + status = napi_set_named_property(env, global, CLASS_NAME.c_str(), constructor); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("Init:set global named property fail")); + + status = napi_set_named_property(env, exports, CLASS_NAME.c_str(), constructor); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("set named property fail")); + + status = napi_define_properties(env, exports, IMG_ARRAY_SIZE(static_prop), static_prop); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("define properties fail")); + + EFFECT_LOG_I("Init success"); + return exports; +} + +napi_value ColorPickerNapi::Constructor(napi_env env, napi_callback_info info) +{ + napi_value undefineVar = nullptr; + napi_get_undefined(env, &undefineVar); + + napi_status status; + napi_value thisVar = nullptr; + napi_get_undefined(env, &thisVar); + + EFFECT_LOG_I("Constructor IN"); + IMG_JS_NO_ARGS(env, info, status, thisVar); + + IMG_NAPI_CHECK_RET(IMG_IS_READY(status, thisVar), undefineVar); + std::unique_ptr pColorPickerNapi = std::make_unique(); + + IMG_NAPI_CHECK_RET(IMG_NOT_NULL(pColorPickerNapi), undefineVar); + + pColorPickerNapi->env_ = env; + pColorPickerNapi->nativeColorPicker_ = sColorPicker_; + + status = napi_wrap(env, thisVar, + reinterpret_cast(pColorPickerNapi.get()), + Destructor, + nullptr, + &(pColorPickerNapi->wrapper_)); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + undefineVar, + EFFECT_LOG_E("Failure wrapping js to native napi")); + + pColorPickerNapi.release(); + sColorPicker_ = nullptr; + + return thisVar; +} + +void ColorPickerNapi::Destructor(napi_env env, void* nativeObject, void* finalize) +{ + ColorPickerNapi *pColorPickerNapi = reinterpret_cast(nativeObject); + + if (IMG_NOT_NULL(pColorPickerNapi)) { + pColorPickerNapi->~ColorPickerNapi(); + } +} + +static void CreateColorPickerFromPixelmapExecute(napi_env env, void* data) +{ + EFFECT_LOG_I("create ColorPicker Execute"); + auto context = static_cast(data); + uint32_t errorCode = ERR_EFFECT_INVALID_VALUE; + context->rColorPicker = ColorPicker::CreateColorPicker(context->rPixelMap, errorCode); + + context->status = ERROR; + if (IMG_NOT_NULL(context->rColorPicker) && errorCode == SUCCESS) { + context->status = SUCCESS; + } +} + +void ColorPickerNapi::CreateColorPickerFromPixelmapComplete(napi_env env, napi_status status, void* data) +{ + napi_value constructor = nullptr; + napi_value result = nullptr; + + EFFECT_LOG_I("Create ColorPicker Complete"); + auto context = static_cast(data); + status = napi_get_reference_value(env, sConstructor_, &constructor); + if (IMG_IS_OK(status)) { + sColorPicker_ = context->rColorPicker; + status = napi_new_instance(env, constructor, NUM_0, nullptr, &result); + } + + if (!IMG_IS_OK(status)) { + context->status = ERROR; + EFFECT_LOG_E("New instance could not be obtained"); + napi_get_undefined(env, &result); + } + + CommonCallbackRoutine(env, context, result); +} + +static void CreateColorPickerErrorComplete(napi_env env, napi_status status, void* data) +{ + napi_value result = nullptr; + napi_get_undefined(env, &result); + auto context = static_cast(data); + context->status = ERROR; + CommonCallbackRoutine(env, context, result); +} + +napi_value ColorPickerNapi::CreateColorPicker(napi_env env, napi_callback_info info) +{ + napi_value result = nullptr; + napi_get_undefined(env, &result); + int32_t refCount = 1; + napi_status status; + napi_value thisVar = nullptr; + napi_value argValue[NUM_4] = {0}; + size_t argCount = NUM_4; + ImageType imgType = ImageType::TYPE_UNKOWN; + EFFECT_LOG_I("[ColorPickerNapi]Create ColorPicker IN"); + IMG_JS_ARGS(env, info, status, argCount, argValue, thisVar); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), nullptr, EFFECT_LOG_E("fail to napi_get_cb_info")); + std::unique_ptr asyncContext = std::make_unique(); + if (argCount >= NUM_1) { + imgType = ParserArgumentType(env, argValue[NUM_1 - 1]); + if (imgType == ImageType::TYPE_PIXEL_MAP) { + asyncContext->rPixelMap = Media::PixelMapNapi::GetPixelMap(env, argValue[NUM_1 - 1]); + BuildMsgOnError(env, asyncContext, IMG_NOT_NULL(asyncContext->rPixelMap), "Pixmap mismatch"); + } else { + BuildMsgOnError(env, asyncContext, false, "image type mismatch"); + } + } + IMG_NAPI_CHECK_RET_D(asyncContext->errorMsg == nullptr, nullptr, EFFECT_LOG_E("image type mismatch.")); + if (argCount == NUM_2 && Media::ImageNapiUtils::getType(env, argValue[argCount - 1]) == napi_function) { + napi_create_reference(env, argValue[argCount - 1], refCount, &asyncContext->callbackRef); + } + if (asyncContext->callbackRef == nullptr) { + napi_create_promise(env, &(asyncContext->deferred), &result); + } + if (asyncContext->errorMsg != nullptr) { + IMG_CREATE_CREATE_ASYNC_WORK(env, status, + "CreateColorPickerError", + [](napi_env env, void* data) {}, + CreateColorPickerErrorComplete, + asyncContext, + asyncContext->work); + } else if (imgType == ImageType::TYPE_PIXEL_MAP) { + IMG_CREATE_CREATE_ASYNC_WORK(env, status, + "CreateColorPickerFromPixelMap", + CreateColorPickerFromPixelmapExecute, + CreateColorPickerFromPixelmapComplete, + asyncContext, asyncContext->work); + } else { + EFFECT_LOG_E("Create error"); + } + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), nullptr, EFFECT_LOG_E("fail to create async work")); + return result; +} + +napi_value ColorPickerNapi::GetScaledPixelMap(napi_env env, napi_callback_info info) +{ + napi_status status; + napi_value thisVar = nullptr; + EFFECT_LOG_I("GetScaledPixelMap"); + IMG_JS_NO_ARGS(env, info, status, thisVar); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("fail to napi_get_cb_info")); + ColorPickerNapi *thisColorPicker = nullptr; + + status = napi_unwrap(env, thisVar, reinterpret_cast(&thisColorPicker)); + IMG_NAPI_CHECK_RET_D(IMG_IS_READY(status, thisColorPicker), + nullptr, + EFFECT_LOG_E("fail to unwrap context")); + + IMG_NAPI_CHECK_RET_D(IMG_IS_READY(status, thisColorPicker->nativeColorPicker_), + nullptr, + EFFECT_LOG_E("empty native colorPicker")); + + auto result = thisColorPicker->nativeColorPicker_->GetScaledPixelMap(); + IMG_NAPI_CHECK_RET_D(IMG_IS_READY(status, result), + nullptr, + EFFECT_LOG_E("empty pixelmap")); + + EFFECT_LOG_I("GetPixelMap.w,h=%{public}d,%{public}d", result->GetWidth(), result->GetHeight()); + return Media::PixelMapNapi::CreatePixelMap(env, result); +} + +static void GetMainColorExecute(napi_env env, void* data) +{ + EFFECT_LOG_I("[ColorPicker]Get color execute"); + uint32_t errorCode = ERR_EFFECT_INVALID_VALUE; + auto context = static_cast(data); + errorCode = context->rColorPicker->GetMainColor(context->color); + if (errorCode == SUCCESS) { + context->status = SUCCESS; + } else { + context->status = ERROR; + } +} + +static void GetMainColorComplete(napi_env env, napi_status status, void* data) +{ + EFFECT_LOG_I("[ColorPicker]Get color Complete"); + napi_value result = nullptr; + napi_get_undefined(env, &result); + auto context = static_cast(data); + if (context->status == SUCCESS) { + EFFECT_LOG_I("[ColorPicker]build color"); + result = BuildJsColor(env, context->color); + } + EFFECT_LOG_I("[ColorPicker]Get color[ARGB] %{public}f,%{public}f,%{public}f,%{public}f", + context->color.a, + context->color.r, + context->color.g, + context->color.b); + CommonCallbackRoutine(env, context, result); +} + +napi_value ColorPickerNapi::GetMainColor(napi_env env, napi_callback_info info) +{ + napi_value result = nullptr; + int32_t refCount = 1; + napi_status status; + napi_value thisVar = nullptr; + napi_value argValue[NUM_1] = {0}; + size_t argCount = 1; + EFFECT_LOG_I("Get MainColor"); + IMG_JS_ARGS(env, info, status, argCount, argValue, thisVar); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("fail to napi_get_cb_info")); + + std::unique_ptr asyncContext = std::make_unique(); + status = napi_unwrap(env, thisVar, reinterpret_cast(&asyncContext->nConstructor)); + IMG_NAPI_CHECK_RET_D(IMG_IS_READY(status, asyncContext->nConstructor), + nullptr, + EFFECT_LOG_E("fail to unwrap context")); + asyncContext->rColorPicker = asyncContext->nConstructor->nativeColorPicker_; + IMG_NAPI_CHECK_RET_D(IMG_IS_READY(status, asyncContext->rColorPicker), + nullptr, + EFFECT_LOG_E("empty native ColorPicker")); + if (argCount == NUM_1 && Media::ImageNapiUtils::getType(env, argValue[argCount - 1]) == napi_function) { + napi_create_reference(env, argValue[argCount - 1], refCount, &asyncContext->callbackRef); + } + if (asyncContext->callbackRef == nullptr) { + napi_create_promise(env, &(asyncContext->deferred), &result); + } else { + napi_get_undefined(env, &result); + } + + IMG_CREATE_CREATE_ASYNC_WORK(env, status, "GetMainColor", + GetMainColorExecute, + GetMainColorComplete, + asyncContext, asyncContext->work); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("fail to create async work")); + return result; +} + +napi_value BuildJsColor(napi_env env, ColorManager::Color color) +{ + EFFECT_LOG_I("build color"); + napi_value result = nullptr; + napi_value clrRed = nullptr; + napi_value clrGreen = nullptr; + napi_value clrBlue = nullptr; + napi_value clrAlpha = nullptr; + + napi_create_object(env, &result); + + int color_red = static_cast(color.r * 255.0f); + int color_green = static_cast(color.g * 255.0f); + int color_blue = static_cast(color.b * 255.0f); + int color_alpha = static_cast(color.a * 255.0f); + + napi_create_int32(env, color_red, &clrRed); + napi_set_named_property(env, result, "red", clrRed); + + napi_create_int32(env, color_green, &clrGreen); + napi_set_named_property(env, result, "green", clrGreen); + + napi_create_int32(env, color_blue, &clrBlue); + napi_set_named_property(env, result, "blue", clrBlue); + + napi_create_int32(env, color_alpha, &clrAlpha); + napi_set_named_property(env, result, "alpha", clrAlpha); + + return result; +} + + +napi_value ColorPickerNapi::GetMainColorSync(napi_env env, napi_callback_info info) +{ + napi_status status; + napi_value thisVar = nullptr; + napi_value argValue[NUM_1] = {0}; + size_t argCount = 1; + EFFECT_LOG_I("Get MainColor sync"); + IMG_JS_ARGS(env, info, status, argCount, argValue, thisVar); + IMG_NAPI_CHECK_RET_D(IMG_IS_OK(status), + nullptr, + EFFECT_LOG_E("fail to napi_get_cb_info")); + + ColorPickerNapi *thisColorPicker = nullptr; + + status = napi_unwrap(env, thisVar, reinterpret_cast(&thisColorPicker)); + IMG_NAPI_CHECK_RET_D(IMG_IS_READY(status, thisColorPicker), + nullptr, + EFFECT_LOG_E("fail to unwrap context")); + + IMG_NAPI_CHECK_RET_D(IMG_IS_READY(status, thisColorPicker->nativeColorPicker_), + nullptr, + EFFECT_LOG_E("empty native ColorPicker")); + + uint32_t errorCode = ERR_EFFECT_INVALID_VALUE; + + napi_value result = nullptr; + ColorManager::Color color; + errorCode = thisColorPicker->nativeColorPicker_->GetMainColor(color); + if (errorCode == SUCCESS) { + result = BuildJsColor(env, color); + } else { + napi_get_undefined(env, &result); + } + return result; +} + +ImageType ColorPickerNapi::ParserArgumentType(napi_env env, napi_value argv) +{ + napi_value constructor = nullptr; + napi_value global = nullptr; + bool isInstance = false; + napi_status ret = napi_invalid_arg; + + napi_get_global(env, &global); + + ret = napi_get_named_property(env, global, "ImageSource", &constructor); + if (ret != napi_ok) { + EFFECT_LOG_E("Get ImageSourceNapi property failed!"); + } + + ret = napi_instanceof(env, argv, constructor, &isInstance); + if (ret == napi_ok && isInstance) { + EFFECT_LOG_I("This is ImageSourceNapi type!"); + return ImageType::TYPE_IMAGE_SOURCE; + } + + ret = napi_get_named_property(env, global, "PixelMap", &constructor); + if (ret != napi_ok) { + EFFECT_LOG_E("Get PixelMapNapi property failed!"); + } + + ret = napi_instanceof(env, argv, constructor, &isInstance); + if (ret == napi_ok && isInstance) { + EFFECT_LOG_I("This is PixelMapNapi type!"); + return ImageType::TYPE_PIXEL_MAP; + } + + EFFECT_LOG_E("InValued type!"); + return ImageType::TYPE_UNKOWN; +} + +void BuildMsgOnError(napi_env env, + const std::unique_ptr& context, + bool assertion, + const std::string msg) +{ + if (!assertion) { + EFFECT_LOG_E("%{public}s", msg.c_str()); + napi_create_string_utf8(env, msg.c_str(), NAPI_AUTO_LENGTH, &(context->errorMsg)); + } +} +} // namespace Rosen +} // namespace OHOS diff --git a/interfaces/kits/napi/graphic/effect_kit/src/native_module_ohos_effect.cpp b/interfaces/kits/napi/graphic/effect_kit/src/native_module_ohos_effect.cpp new file mode 100644 index 0000000000..d05c468c10 --- /dev/null +++ b/interfaces/kits/napi/graphic/effect_kit/src/native_module_ohos_effect.cpp @@ -0,0 +1,54 @@ +/* + * Copyright (C) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "native_module_ohos_effect.h" +#include "hilog/log.h" +#include "effect_utils.h" + +using OHOS::HiviewDFX::HiLog; +namespace OHOS { +namespace Rosen { +/* + * Function registering all props and functions of ohos.effectlibrary module + */ +static napi_value Export(napi_env env, napi_value exports) +{ + EFFECT_LOG_I("ColorPicker Napi CALL"); + ColorPickerNapi::Init(env, exports); + return exports; +} + +/* + * module define + */ +static napi_module g_module = { + .nm_version = 1, + .nm_flags = 0, + .nm_filename = nullptr, + .nm_register_func = Export, + .nm_modname = "effect_kit", + .nm_priv = ((void*)0), + .reserved = {0} +}; + +/* + * module register + */ +extern "C" __attribute__((constructor)) void RegisterModule(void) +{ + napi_module_register(&g_module); +} +} // namespace Rosen +} // namespace OHOS diff --git a/rosen/modules/effect/color_picker/BUILD.gn b/rosen/modules/effect/color_picker/BUILD.gn new file mode 100644 index 0000000000..0e2afef829 --- /dev/null +++ b/rosen/modules/effect/color_picker/BUILD.gn @@ -0,0 +1,77 @@ +# Copyright (c) 2022 Huawei Device Co., Ltd. +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +import("//build/ohos.gni") +import("//foundation/graphic/graphic_2d/graphic_config.gni") +import("//foundation/graphic/graphic_2d/rosen/modules/effect/effect_config.gni") + +## Build libcolor_picker.so + +config("graphic_napi_color_picker_config") { + visibility = [ ":*" ] + + cflags = [ + "-Wall", + "-Werror", + "-g3", + "-Wno-pointer-arith", + "-Wno-non-virtual-dtor", + "-Wno-missing-field-initializers", + "-Wno-c++11-narrowing", + ] + + defines = [ "EGL_EGLEXT_PROTOTYPES" ] +} + +ohos_shared_library("color_picker") { + include_dirs = [ + "include", + "//foundation/graphic/graphic_2d/interfaces/inner_api/surface", + "//foundation/graphic/graphic_2d/interfaces/kits/napi/graphic/effect/include", + "//foundation/multimedia/image_standard/interfaces/innerkits/include/", + "//foundation/graphic/graphic_2d/utils/color_manager/export", + "//foundation/graphic/graphic_2d/utils/log", + ] + + configs = [ + ":graphic_napi_color_picker_config", + "//utils/native/base:utils_config", + ] + + sources = [ "./src/color_picker.cpp" ] + + deps = [ + "//base/hiviewdfx/hilog/interfaces/native/innerkits:libhilog", + "//foundation/arkui/napi:ace_napi", + "//foundation/graphic/graphic_2d:libsurface", + "//foundation/graphic/graphic_2d/rosen/modules/effect/effectChain:libeffectchain", + "//foundation/graphic/graphic_2d/rosen/modules/effect/egl:libegl_effect", + "//foundation/graphic/graphic_2d/utils/color_manager:color_manager", + "//foundation/multimedia/image_standard/frameworks/innerkitsimpl/pixelconverter:pixelconvertadapter", + "//foundation/multimedia/image_standard/interfaces/innerkits:image", + "//foundation/multimedia/image_standard/interfaces/innerkits:image_native", + "//third_party/flutter/build/skia:ace_skia_ohos", + "//utils/native/base:utils", + ] + + deps += [ "//foundation/graphic/graphic_2d:libgl" ] + + external_deps = [ "hitrace_native:hitrace_meter" ] + + cflags_cc = [ "-std=c++17" ] + + relative_install_dir = "module" + part_name = "graphic_standard" + subsystem_name = "graphic" +} +## Build color_picker.so diff --git a/rosen/modules/effect/color_picker/include/color_picker.h b/rosen/modules/effect/color_picker/include/color_picker.h new file mode 100644 index 0000000000..eda266f89c --- /dev/null +++ b/rosen/modules/effect/color_picker/include/color_picker.h @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2022 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef COLOR_PICKER_H +#define COLOR_PICKER_H + +#include +#include "effect_type.h" + +#ifdef __cplusplus +extern "C" { +#endif + +namespace OHOS { +namespace Media { +class PixelMap; +} +namespace ColorManager { +class Color; +} +namespace Rosen { +class ColorPicker { +public: + ~ColorPicker() {} + NATIVEEXPORT static std::shared_ptr CreateColorPicker(const std::shared_ptr& pixmap, + uint32_t &errorCode); + NATIVEEXPORT std::shared_ptr GetScaledPixelMap(); + NATIVEEXPORT uint32_t GetMainColor(ColorManager::Color &color); + +private: + ColorPicker(std::shared_ptr pixmap); + + // variables + std::shared_ptr pixelmap_; +}; +} // namespace Rosen +} // namespace OHOS + +#ifdef __cplusplus +} +#endif + +#endif // COLOR_PICKER_H diff --git a/rosen/modules/effect/color_picker/include/effect_errors.h b/rosen/modules/effect/color_picker/include/effect_errors.h new file mode 100644 index 0000000000..276c1bc26d --- /dev/null +++ b/rosen/modules/effect/color_picker/include/effect_errors.h @@ -0,0 +1,30 @@ +/* + * Copyright (C) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef EFFECT_ERRORS_H +#define EFFECT_ERRORS_H + +#include +#include "errors.h" + +namespace OHOS { +namespace Rosen { +/* Effect defined errors */ +const uint32_t ERR_EFFECT_INVALID_VALUE = 2; // Invalid value +const uint32_t ERROR = 1; // Operation error +const uint32_t SUCCESS = 0; // Operation success +} // namespace Rosen +} // namespace OHOS +#endif // EFFECT_ERRORS_H diff --git a/rosen/modules/effect/color_picker/include/effect_type.h b/rosen/modules/effect/color_picker/include/effect_type.h new file mode 100644 index 0000000000..1590398a4f --- /dev/null +++ b/rosen/modules/effect/color_picker/include/effect_type.h @@ -0,0 +1,31 @@ +/* + * Copyright (C) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef EFFECT_TYPE_H +#define EFFECT_TYPE_H + +#include + +namespace OHOS { +namespace Rosen { +#ifdef _WIN32 +#define NATIVEEXPORT __declspec(dllexport) +#else +#define NATIVEEXPORT +#endif +} // namespace Rosen +} // namespace OHOS + +#endif // EFFECT_TYPE_H diff --git a/rosen/modules/effect/color_picker/include/effect_utils.h b/rosen/modules/effect/color_picker/include/effect_utils.h new file mode 100644 index 0000000000..1539a743e8 --- /dev/null +++ b/rosen/modules/effect/color_picker/include/effect_utils.h @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2022 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef EFFECT_UTILS_H +#define EFFECT_UTILS_H + +#include + +#include "napi/native_api.h" +#include "napi/native_common.h" +#include "napi/native_node_api.h" + +namespace OHOS { +namespace Rosen { +constexpr OHOS::HiviewDFX::HiLogLabel LABEL = {LOG_CORE, LOG_DOMAIN, "EffectNapi"}; +#define EFFECT_LOG_I(fmt, ...) OHOS::HiviewDFX::HiLog::Info(LABEL, \ + "%{public}s:%{public}d " fmt, __func__, __LINE__, ##__VA_ARGS__) + +#define EFFECT_LOG_E(fmt, ...) OHOS::HiviewDFX::HiLog::Error(LABEL, \ + "%{public}s:%{public}d " fmt, __func__, __LINE__, ##__VA_ARGS__) +} // namespace Rosen +} // namespace OHOS +#endif // EFFECT_UTILS_H diff --git a/rosen/modules/effect/color_picker/src/color_picker.cpp b/rosen/modules/effect/color_picker/src/color_picker.cpp new file mode 100644 index 0000000000..bf9c4cce75 --- /dev/null +++ b/rosen/modules/effect/color_picker/src/color_picker.cpp @@ -0,0 +1,106 @@ +/* + * Copyright (c) 2022 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "color_picker.h" +#include "hilog/log.h" +#include "effect_errors.h" +#include "effect_utils.h" +#include "color.h" +#include "pixel_map.h" +#include "include/core/SkBitmap.h" +#include "include/core/SkRect.h" +#include "include/core/SkImageFilter.h" +#include "include/effects/SkImageFilters.h" +#include "include/core/SkCanvas.h" +#include "include/core/SkColor.h" +#include "include/core/SkColorFilter.h" +#include "include/core/SkColorSpace.h" +#include "include/core/SkImageInfo.h" +#include "include/core/SkPaint.h" +#include "include/core/SkPixmap.h" +#include "include/core/SkFont.h" +#include "include/core/SkTypeface.h" + +#ifdef __cplusplus +extern "C" { +#endif + +namespace OHOS { +namespace Rosen { +using OHOS::HiviewDFX::HiLog; + +std::shared_ptr ColorPicker::CreateColorPicker(const std::shared_ptr& pixmap, + uint32_t &errorCode) +{ + if (pixmap == nullptr) { + HiLog::Info(LABEL, "[ColorPicker]failed to create ColorPicker with null pixmap."); + errorCode = ERR_EFFECT_INVALID_VALUE; + return nullptr; + } + ColorPicker *colorPicker = new (std::nothrow) ColorPicker(pixmap); + if (colorPicker == nullptr) { + HiLog::Info(LABEL, "[ColorPicker]failed to create ColorPicker with pixmap."); + errorCode = ERR_EFFECT_INVALID_VALUE; + return nullptr; + } + errorCode = SUCCESS; + return std::shared_ptr(colorPicker); +} + +std::shared_ptr ColorPicker::GetScaledPixelMap() +{ + // Create scaled pixelmap + OHOS::Media::InitializationOptions options; + options.alphaType = pixelmap_->GetAlphaType(); + options.pixelFormat = pixelmap_->GetPixelFormat(); + options.scaleMode = OHOS::Media::ScaleMode::FIT_TARGET_SIZE; + options.size.width = 1; + options.size.height = 1; + options.editable = true; + std::unique_ptr newPixelMap = Media::PixelMap::Create(*pixelmap_.get(), options); + return std::move(newPixelMap); +} + +uint32_t ColorPicker::GetMainColor(ColorManager::Color &color) +{ + if (pixelmap_ == nullptr) { + return ERR_EFFECT_INVALID_VALUE; + } + std::shared_ptr pixelMap = GetScaledPixelMap(); + + // get color + uint32_t colorVal = 0; + int x = 0; + int y = 0; + bool bSucc = pixelMap->GetARGB32Color(x, y, colorVal); + HiLog::Info(LABEL, "[newpix].argb.ret=%{public}d, %{public}x", bSucc, colorVal); + color = ColorManager::Color(colorVal); + return SUCCESS; +} + + +ColorPicker::ColorPicker(std::shared_ptr pixmap) +{ + if (pixmap == nullptr) { + return ; + } + pixelmap_ = pixmap; +} +} // namespace Rosen +} // namespace OHOS + +#ifdef __cplusplus +} +#endif diff --git a/rosen/modules/effect/test/unittest/BUILD.gn b/rosen/modules/effect/test/unittest/BUILD.gn index 8cf1b60437..4240116f0a 100644 --- a/rosen/modules/effect/test/unittest/BUILD.gn +++ b/rosen/modules/effect/test/unittest/BUILD.gn @@ -19,7 +19,6 @@ module_output_path = "graphic_standard/rosen/modules/effect" ohos_unittest("EffectTest") { module_out_path = module_output_path - sources = [] deps = [ "//base/hiviewdfx/hilog/interfaces/native/innerkits:libhilog", @@ -27,17 +26,27 @@ ohos_unittest("EffectTest") { "//utils/native/base:utils", ] + sources = [] + if (effect_enable_gpu) { sources += [ "effect_chain_unittest.cpp" ] - - deps += [ - "//foundation/graphic/graphic_2d:libgl", - "//foundation/graphic/graphic_2d/rosen/modules/effect/effectChain:libeffectchain", - "//foundation/graphic/graphic_2d/rosen/modules/effect/egl:libegl_effect", - ] } - configs = [ ":effect_test_config" ] + deps += [ + "//foundation/graphic/graphic_2d:libgl", + "//foundation/graphic/graphic_2d/rosen/modules/effect/color_picker:color_picker", + "//foundation/graphic/graphic_2d/rosen/modules/effect/effectChain:libeffectchain", + "//foundation/graphic/graphic_2d/rosen/modules/effect/egl:libegl_effect", + "//foundation/graphic/graphic_2d/utils/color_manager:color_manager", + "//foundation/multimedia/image_standard/interfaces/innerkits:image", + "//foundation/multimedia/image_standard/interfaces/innerkits:image_native", + "//third_party/flutter/build/skia:ace_skia_ohos", + ] + + configs = [ + ":effect_test_config", + "//foundation/graphic/graphic_2d/utils/color_manager:color_manager_public_config", + ] } config("effect_test_config") { @@ -45,8 +54,12 @@ config("effect_test_config") { include_dirs = [ "//third_party/EGL/api", "//third_party/openGLES/api", + "//third_party/skia", + "//foundation/graphic/graphic_2d/rosen/modules/effect/color_picker/include", "//foundation/graphic/graphic_2d/rosen/modules/effect/effectChain/include", "//foundation/graphic/graphic_2d/rosen/modules/effect/egl/include", + "//foundation/graphic/graphic_2d/utils/color_manager/export", + "//foundation/multimedia/image_standard/interfaces/innerkits/include/", ] }