From ac10c24fd34bcb98f7b19bf449bcba218ca65549 Mon Sep 17 00:00:00 2001 From: zhangjinyu101 Date: Wed, 17 Jul 2024 00:57:26 +0800 Subject: [PATCH] add statrt action Signed-off-by: zhangjinyu101 Change-Id: Id9539319c554fbcb8e1a92788df85fd6e0b5680c --- .../drag_drop/drag_drop_func_wrapper.cpp | 247 +++++++++++++++++- .../drag_drop/drag_drop_func_wrapper.h | 5 +- .../manager/drag_drop/drag_drop_manager.h | 12 + .../drag_drop/utils/internal_drag_action.h | 83 ++++++ .../core/interfaces/arkoala/arkoala_api.h | 27 ++ .../native/node/drag_adapter_impl.cpp | 120 ++++++++- .../native/node/drag_adapter_impl.h | 8 +- .../core/interfaces/native/node/node_api.cpp | 1 + .../native/event/drag_and_drop_impl.cpp | 181 ++++++++++++- 9 files changed, 667 insertions(+), 17 deletions(-) create mode 100644 frameworks/core/components_ng/manager/drag_drop/utils/internal_drag_action.h diff --git a/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.cpp b/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.cpp index 50557b30b7a..aac1d876c5e 100644 --- a/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.cpp +++ b/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.cpp @@ -13,22 +13,267 @@ * limitations under the License. */ +#include + #include "core/components/theme/blur_style_theme.h" #include "core/components/theme/shadow_theme.h" #include "core/components_ng/manager/drag_drop/drag_drop_func_wrapper.h" #include "core/components_ng/pattern/image/image_pattern.h" +#include "frameworks/core/common/interaction/interaction_interface.h" +#include "frameworks/core/common/ace_engine.h" +#include "core/common/udmf/udmf_client.h" +#include "frameworks/base/json/json_util.h" +#include "frameworks/base/image/pixel_map.h" +#include "frameworks/core/components/common/layout/grid_system_manager.h" +#include "frameworks/core/components_ng/manager/drag_drop/drag_drop_manager.h" namespace OHOS::Ace::NG { -namespace { constexpr float DEFAULT_OPACITY = 0.95f; constexpr Dimension PREVIEW_BORDER_RADIUS = 12.0_vp; constexpr float BLUR_SIGMA_SCALE = 0.57735f; constexpr float SCALE_HALF = 0.5f; constexpr float MIN_OPACITY { 0.0f }; constexpr float MAX_OPACITY { 1.0f }; +using DragNotifyMsg = OHOS::Ace::DragNotifyMsg; +using OnDragCallback = std::function; +using StopDragCallback = std::function; +namespace { +constexpr int32_t MOUSE_POINTER_ID = 1001; +constexpr int32_t SOURCE_TOOL_PEN = 1; +constexpr int32_t SOURCE_TYPE_TOUCH = 2; +constexpr int32_t PEN_POINTER_ID = 102; +constexpr int32_t SOURCE_TYPE_MOUSE = 1; +} + +static bool CheckInternalDragging(const RefPtr& container) +{ + CHECK_NULL_RETURN(container, false); + auto pipelineContext = container->GetPipelineContext(); + if (!pipelineContext || !pipelineContext->IsDragging()) { + return false; + } + return true; +} + +void GetShadowInfoArray( + std::shared_ptr dragAction, std::vector& shadowInfos) +{ + auto minScaleWidth = GridSystemManager::GetInstance().GetMaxWidthWithColumnType(GridColumnType::DRAG_PANEL); + for (auto& pixelMap : dragAction->pixelMapList) { + double scale = 1.0; + if (pixelMap.GetRawPtr()) { + if (pixelMap->GetWidth() > minScaleWidth && dragAction->previewOption.isScaleEnabled) { + scale = minScaleWidth / pixelMap->GetWidth(); + } + auto pixelMapScale = dragAction->windowScale * scale; + pixelMap->Scale(pixelMapScale, pixelMapScale, AceAntiAliasingOption::HIGH); + } + int32_t width = pixelMap->GetWidth(); + int32_t height = pixelMap->GetHeight(); + double x = dragAction->touchPointX; + double y = dragAction->touchPointY; + if (!dragAction->hasTouchPoint) { + x = -width * PIXELMAP_WIDTH_RATE; + y = -height * PIXELMAP_HEIGHT_RATE; + } + ShadowInfoCore shadowInfo { pixelMap, -x, -y }; + shadowInfos.push_back(shadowInfo); + } } +void PostStopDrag( + std::shared_ptr dragAction, const RefPtr& container) +{ + auto taskExecutor = container->GetTaskExecutor(); + CHECK_NULL_VOID(taskExecutor); + auto windowId = container->GetWindowId(); + taskExecutor->PostTask( + [dragAction, windowId]() { + CHECK_NULL_VOID(dragAction); + TAG_LOGI(AceLogTag::ACE_DRAG, "drag state is reject, stop drag, windowId is %{public}d.", windowId); + OHOS::Ace::DragDropRet dropResult { OHOS::Ace::DragRet::DRAG_CANCEL, false, windowId, + OHOS::Ace::DragBehavior::UNKNOWN }; + InteractionInterface::GetInstance()->StopDrag(dropResult); + InteractionInterface::GetInstance()->SetDragWindowVisible(false); + }, + TaskExecutor::TaskType::UI, "ArkUIDragStop"); +} + +bool ConfirmCurPointerEventInfo( + std::shared_ptr dragAction, const RefPtr& container) +{ + CHECK_NULL_RETURN(dragAction, false); + CHECK_NULL_RETURN(container, false); + StopDragCallback stopDragCallback = [dragAction, container]() { + CHECK_NULL_VOID(dragAction); + CHECK_NULL_VOID(container); + bool needPostStopDrag = false; + if (dragAction->dragState == DragAdapterState::SENDING) { + needPostStopDrag = true; + } + { + std::lock_guard lock(dragAction->dragStateMutex); + dragAction->dragState = DragAdapterState::REJECT; + } + if (needPostStopDrag) { + PostStopDrag(dragAction, container); + } + }; + int32_t sourceTool = -1; + bool getPointSuccess = container->GetCurPointerEventInfo(dragAction->pointer, dragAction->x, dragAction->y, + dragAction->sourceType, sourceTool, std::move(stopDragCallback)); + if (dragAction->sourceType == SOURCE_TYPE_MOUSE) { + dragAction->pointer = MOUSE_POINTER_ID; + } else if (dragAction->sourceType == SOURCE_TYPE_TOUCH && sourceTool == SOURCE_TOOL_PEN) { + dragAction->pointer = PEN_POINTER_ID; + } + return getPointSuccess; +} + +void EnvelopedDragData( + std::shared_ptr dragAction, std::optional& dragData) +{ + auto container = AceEngine::Get().GetContainer(dragAction->instanceId); + CHECK_NULL_VOID(container); + auto displayInfo = container->GetDisplayInfo(); + CHECK_NULL_VOID(displayInfo); + dragAction->displayId = displayInfo->GetDisplayId(); + std::vector shadowInfos; + GetShadowInfoArray(dragAction, shadowInfos); + if (shadowInfos.empty()) { + TAG_LOGE(AceLogTag::ACE_DRAG, "shadowInfo array is empty"); + return; + } + auto pointerId = dragAction->pointer; + std::string udKey; + std::map summary; + int32_t dataSize = 1; + if (dragAction->unifiedData) { + int32_t ret = UdmfClient::GetInstance()->SetData(dragAction->unifiedData, udKey); + if (ret != 0) { + TAG_LOGI(AceLogTag::ACE_DRAG, "udmf set data failed, return value is %{public}d", ret); + } else { + ret = UdmfClient::GetInstance()->GetSummary(udKey, summary); + if (ret != 0) { + TAG_LOGI(AceLogTag::ACE_DRAG, "get summary failed, return value is %{public}d", ret); + } + } + dataSize = static_cast(dragAction->unifiedData->GetSize()); + } + int32_t recordSize = (dataSize != 0 ? dataSize : static_cast(shadowInfos.size())); + if (dragAction->previewOption.isNumber) { + recordSize = dragAction->previewOption.badgeNumber > 1 ? dragAction->previewOption.badgeNumber : 1; + } else if (!dragAction->previewOption.isShowBadge) { + recordSize = 1; + } + auto windowId = container->GetWindowId(); + auto arkExtraInfoJson = JsonUtil::Create(true); + auto pipeline = container->GetPipelineContext(); + CHECK_NULL_VOID(pipeline); + dragAction->dipScale = pipeline->GetDipScale(); + arkExtraInfoJson->Put("dip_scale", dragAction->dipScale); + NG::DragDropFuncWrapper::UpdateExtraInfo(arkExtraInfoJson, dragAction->previewOption); + dragData = { shadowInfos, {}, udKey, dragAction->extraParams, arkExtraInfoJson->ToString(), dragAction->sourceType, + recordSize, pointerId, dragAction->x, dragAction->y, dragAction->displayId, windowId, true, false, summary }; +} + +void HandleCallback(std::shared_ptr dragAction, + const OHOS::Ace::DragNotifyMsg& dragNotifyMsg, const DragAdapterStatus& dragStatus) +{ + TAG_LOGI(AceLogTag::ACE_DRAG, "drag notify message result is %{public}d.", dragNotifyMsg.result); + CHECK_NULL_VOID(dragAction); + bool hasHandle = false; + { + std::lock_guard lock(dragAction->mutex); + hasHandle = dragAction->hasHandle; + dragAction->hasHandle = true; + } + if (hasHandle) { + return; + } + auto container = AceEngine::Get().GetContainer(dragAction->instanceId); + CHECK_NULL_VOID(container); + if (dragStatus == DragAdapterStatus::ENDED) { + auto pipelineContext = container->GetPipelineContext(); + CHECK_NULL_VOID(pipelineContext); + pipelineContext->ResetDragging(); + } + int32_t dragState = static_cast(dragStatus); + dragAction->callback(dragNotifyMsg, dragState); +} + +int32_t CheckStartAction(std::shared_ptr dragAction, + const RefPtr& container, const RefPtr& manager) +{ + if (CheckInternalDragging(container)) { + return -1; + } + { + std::lock_guard lock(dragAction->dragStateMutex); + if (manager->GetDragAction() != nullptr && (manager->GetDragAction())->dragState == DragAdapterState::SENDING) { + return -1; + } + dragAction->dragState = DragAdapterState::SENDING; + } + DragDropFuncWrapper::UpdatePreviewOptionDefaultAttr(dragAction->previewOption); + auto isGetPointSuccess = ConfirmCurPointerEventInfo(dragAction, container); + if (!isGetPointSuccess) { + return -1; + } + return 0; +} + +int32_t DragDropFuncWrapper::StartDragAction(std::shared_ptr dragAction) +{ + auto pipelineContext = PipelineContext::GetContextByContainerId(dragAction->instanceId); + CHECK_NULL_RETURN(pipelineContext, -1); + auto manager = pipelineContext->GetDragDropManager(); + CHECK_NULL_RETURN(manager, -1); + auto container = AceEngine::Get().GetContainer(dragAction->instanceId); + CHECK_NULL_RETURN(container, -1); + auto windowScale = container->GetWindowScale(); + CHECK_NULL_RETURN(windowScale, -1); + dragAction->windowScale = windowScale; + manager->SetDragAction(dragAction); + if (CheckStartAction(dragAction, container, manager) == -1) { + manager->GetDragAction()->dragState = DragAdapterState::INIT; + return -1; + } + std::optional dragData; + EnvelopedDragData(dragAction, dragData); + if (!dragData) { + manager->GetDragAction()->dragState = DragAdapterState::INIT; + return -1; + } + OnDragCallback callback = [dragAction, manager](const OHOS::Ace::DragNotifyMsg& dragNotifyMsg) { + { + std::lock_guard lock(dragAction->dragStateMutex); + dragAction->dragState = DragAdapterState::INIT; + manager->SetDragAction(dragAction); + } + HandleCallback(dragAction, dragNotifyMsg, DragAdapterStatus::ENDED); + }; + NG::DragDropFuncWrapper::SetDraggingPointerAndPressedState(dragAction->pointer, dragAction->instanceId); + int32_t ret = InteractionInterface::GetInstance()->StartDrag(dragData.value(), callback); + if (ret != 0) { + manager->GetDragAction()->dragState = DragAdapterState::INIT; + return -1; + } + HandleCallback(dragAction, DragNotifyMsg {}, DragAdapterStatus::STARTED); + pipelineContext->SetIsDragging(true); + std::lock_guard lock(dragAction->dragStateMutex); + if (dragAction->dragState == DragAdapterState::SENDING) { + dragAction->dragState = DragAdapterState::SUCCESS; + InteractionInterface::GetInstance()->SetDragWindowVisible(true); + auto pipelineContext = container->GetPipelineContext(); + pipelineContext->OnDragEvent( + { dragAction->x, dragAction->y }, DragEventAction::DRAG_EVENT_START_FOR_CONTROLLER); + NG::DragDropFuncWrapper::DecideWhetherToStopDragging( + { dragAction->x, dragAction->y }, dragAction->extraParams, dragAction->pointer, dragAction->instanceId); + } + return 0; +} void DragDropFuncWrapper::SetDraggingPointerAndPressedState(int32_t currentPointerId, int32_t containerId) { auto pipelineContext = PipelineContext::GetContextByContainerId(containerId); diff --git a/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.h b/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.h index 9e72514e397..2b43d1761e4 100644 --- a/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.h +++ b/frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.h @@ -28,9 +28,10 @@ namespace OHOS::Ace::NG { class FrameNode; class ACE_FORCE_EXPORT DragDropFuncWrapper { public: + static int32_t StartDragAction(std::shared_ptr dragAction); static void SetDraggingPointerAndPressedState(int32_t currentPointerId, int32_t containerId); - static void DecideWhetherToStopDragging(const PointerEvent& pointerEvent, - const std::string& extraParams, int32_t currentPointerId, int32_t containerId); + static void DecideWhetherToStopDragging(const PointerEvent& pointerEvent, const std::string& extraParams, + int32_t currentPointerId, int32_t containerId); static void UpdateDragPreviewOptionsFromModifier( std::function)> applyOnNodeSync, DragPreviewOption& options); static void UpdatePreviewOptionDefaultAttr(DragPreviewOption& option); diff --git a/frameworks/core/components_ng/manager/drag_drop/drag_drop_manager.h b/frameworks/core/components_ng/manager/drag_drop/drag_drop_manager.h index 21bc8e58ad8..7471d35f0dd 100644 --- a/frameworks/core/components_ng/manager/drag_drop/drag_drop_manager.h +++ b/frameworks/core/components_ng/manager/drag_drop/drag_drop_manager.h @@ -26,6 +26,7 @@ #include "core/components_ng/base/frame_node.h" #include "core/components_ng/manager/drag_drop/drag_drop_proxy.h" #include "core/gestures/velocity_tracker.h" +#include "core/components_ng/manager/drag_drop/utils/internal_drag_action.h" namespace OHOS::Ace { class UnifiedData; @@ -219,6 +220,11 @@ public: dragCursorStyleCore_ = dragCursorStyleCore; } + std::shared_ptr GetDragAction() + { + return dragAction_; + } + RefPtr FindTargetInChildNodes(const RefPtr parentNode, std::vector> hitFrameNodes, bool findDrop); @@ -446,6 +452,11 @@ public: } bool IsDropAllowed(const RefPtr& dragFrameNode); + + void SetDragAction(const std::shared_ptr& dragAction) + { + dragAction_ = dragAction; + } void AddNewDragAnimation() { @@ -561,6 +572,7 @@ private: OffsetF dragMovePosition_ = OffsetF(0.0f, 0.0f); OffsetF lastDragMovePosition_ = OffsetF(0.0f, 0.0f); OffsetF dragTotalMovePosition_ = OffsetF(0.0f, 0.0f); + std::shared_ptr dragAction_; ACE_DISALLOW_COPY_AND_MOVE(DragDropManager); }; diff --git a/frameworks/core/components_ng/manager/drag_drop/utils/internal_drag_action.h b/frameworks/core/components_ng/manager/drag_drop/utils/internal_drag_action.h new file mode 100644 index 00000000000..8eaec01feea --- /dev/null +++ b/frameworks/core/components_ng/manager/drag_drop/utils/internal_drag_action.h @@ -0,0 +1,83 @@ +/* + * Copyright (c) 2024 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 FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_MANAGER_DRAG_DROP_UTILS_INTERAL_DRAG_ACTION_H +#define FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_MANAGER_DRAG_DROP_UTILS_INTERAL_DRAG_ACTION_H + +#include +#include +#include +#include +#include +#include +#include +#include "base/memory/ace_type.h" +#include "base/memory/referenced.h" +#include "core/components_ng/base/frame_node.h" +#include "frameworks/base/geometry/dimension_offset.h" +#include "frameworks/core/gestures/drag_event.h" +#include "frameworks/core/common/interaction/interaction_interface.h" +#include "frameworks/core/components_ng/gestures/gesture_info.h" +#include "frameworks/base/image/pixel_map.h" + +namespace OHOS::Ace::NG { + +enum class DragAdapterState { + INIT, + PENDING, + SENDING, + REJECT, + SUCCESS +}; + +enum class DragAdapterStatus { + UNKNOWN = -1, + STARTED, + ENDED +}; +struct ArkUIInternalDragAndDropInfo { + OHOS::Ace::NG::DragEvent dragEvent; + DragAdapterStatus dragStatus; +}; + +struct ArkUIInteralDragAction { + int32_t instanceId; + int32_t pointer; + void** pixelMapArray; + int32_t size; + int32_t x; + int32_t y; + void* data; + int32_t displayId = 0; + OHOS::Ace::NG::ArkUIInternalDragAndDropInfo* dropInfo; + OHOS::Ace::NG::DragPreviewOption previewOption; + DragAdapterState dragState = DragAdapterState::INIT; + RefPtr unifiedData; + std::string extraParams; + int32_t sourceType = 0; + float dipScale = 0.0; + void* userData; + std::function callback; + float windowScale = 1.0f; + std::mutex mutex; + std::mutex dragStateMutex; + std::vector> pixelMapList; + bool hasHandle = false; + float touchPointX = 0.0; + float touchPointY = 0.0; + bool hasTouchPoint = false; +}; +} // namespace OHOS::Ace::NG +#endif \ No newline at end of file diff --git a/frameworks/core/interfaces/arkoala/arkoala_api.h b/frameworks/core/interfaces/arkoala/arkoala_api.h index e56cb7bf02b..9c69fb1b106 100644 --- a/frameworks/core/interfaces/arkoala/arkoala_api.h +++ b/frameworks/core/interfaces/arkoala/arkoala_api.h @@ -37,6 +37,7 @@ extern "C" { #define ARKUI_NODE_MODIFIERS_API_VERSION 7 #define ARKUI_AUTO_GENERATE_NODE_ID (-2) #define ARKUI_MAX_ANCHOR_ID_SIZE 50 +#define ARKUI_MODIFIER_KEY_COUNT 9 enum ArkUIAPIVariantKind { BASIC = 1, FULL = 2, @@ -1242,8 +1243,15 @@ struct ArkUIAnimator { void* animatorOption; }; +typedef struct { + ArkUIDragEvent* dragEvent; + ArkUI_Int32 status; +} ArkUIDragAndDropInfo; + typedef ArkUIAnimator* ArkUIAnimatorHandle; +typedef void (*DragStatusCallback)(ArkUIDragAndDropInfo* dragAndDropInfo, void* userData); + struct ArkUIImageFrameInfo { ArkUI_CharPtr src; ArkUI_Int32 width; @@ -1340,6 +1348,20 @@ struct ArkUIDragPreViewAndInteractionOptions { struct ArkUI_DialogDismissEvent; typedef ArkUI_DialogDismissEvent* ArkUIDialogDismissEvent; +struct ArkUIDragAction { + ArkUI_Int32 instanceId = -1; + ArkUI_Int32 pointerId = 0; + ArkUI_Float64 touchPointX = 0.0f; + ArkUI_Float64 touchPointY = 0.0f; + void** pixelmapArray; + ArkUI_Int32 size = -1; + ArkUIDragPreViewAndInteractionOptions dragPreviewOption; + void* userData; + DragStatusCallback listener; + void* unifiedData; + bool hasTouchPoint = false; +}; + struct ArkUICommonModifier { void (*setBackgroundColor)(ArkUINodeHandle node, ArkUI_Uint32 color); void (*resetBackgroundColor)(ArkUINodeHandle node); @@ -4845,6 +4867,11 @@ typedef struct { } ArkUINodeAdapterAPI; typedef struct { + ArkUI_Int32 (*startDrag)(ArkUIDragAction* dragAction); + void (*registerStatusListener)(ArkUIDragAction* dragAction, void* userData, DragStatusCallback listener); + void (*unregisterStatusListener)(ArkUIDragAction* dragAction); + ArkUIDragAction* (*createDragActionWithNode)(ArkUINodeHandle node); + ArkUIDragAction* (*createDragActionWithContext)(ArkUIContext* context); void (*setDragPreview)(ArkUINodeHandle node, void* dragPreview); void (*setDragEventStrictReportingEnabledWithNode)(bool enabled); void (*setDragEventStrictReportingEnabledWithContext)(ArkUI_Int32 instanceId, bool enabled); diff --git a/frameworks/core/interfaces/native/node/drag_adapter_impl.cpp b/frameworks/core/interfaces/native/node/drag_adapter_impl.cpp index a796dc2d0f1..910c846772b 100644 --- a/frameworks/core/interfaces/native/node/drag_adapter_impl.cpp +++ b/frameworks/core/interfaces/native/node/drag_adapter_impl.cpp @@ -12,15 +12,120 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -#include "core/interfaces/native/node/drag_adapter_impl.h" +#include "frameworks/core/interfaces/native/node/drag_adapter_impl.h" +#include "native_type.h" + +#include "base/utils/utils.h" #include "core/components_ng/base/frame_node.h" +#include "core/interfaces/arkoala/arkoala_api.h" +#include "core/pipeline_ng/pipeline_context.h" +#include "frameworks/base/image/pixel_map.h" #include "core/components_ng/base/view_abstract.h" +#include "frameworks/core/common/ace_engine.h" #include "core/components_ng/event/gesture_event_hub.h" -#include "core/interfaces/arkoala/arkoala_api.h" +#include "frameworks/core/components_ng/manager/drag_drop/drag_drop_func_wrapper.h" +#include "frameworks/core/components_ng/manager/drag_drop/utils/internal_drag_action.h" namespace OHOS::Ace::DragAdapter { namespace { +static void DragActionConvert( + ArkUIDragAction* dragAction, std::shared_ptr internalDragAction) +{ + internalDragAction->pointer = dragAction->pointerId; + internalDragAction->size = dragAction->size; + auto* pixelMapTemp = reinterpret_cast*>(dragAction->pixelmapArray); + for (int index = 0; index < dragAction->size; index++) { + auto pixelMap = PixelMap::CreatePixelMap(&pixelMapTemp[index]); + internalDragAction->pixelMapList.push_back(pixelMap); + } + internalDragAction->previewOption.isScaleEnabled = dragAction->dragPreviewOption.isScaleEnabled; + if (!internalDragAction->previewOption.isScaleEnabled) { + internalDragAction->previewOption.isDefaultShadowEnabled = dragAction->dragPreviewOption.isDefaultShadowEnabled; + internalDragAction->previewOption.isDefaultRadiusEnabled = dragAction->dragPreviewOption.isDefaultRadiusEnabled; + } + internalDragAction->previewOption.defaultAnimationBeforeLifting = + dragAction->dragPreviewOption.defaultAnimationBeforeLifting; + internalDragAction->previewOption.isMultiSelectionEnabled = dragAction->dragPreviewOption.isMultiSelectionEnabled; + internalDragAction->previewOption.isNumber = dragAction->dragPreviewOption.isNumberBadgeEnabled; + if (dragAction->dragPreviewOption.badgeNumber > 1) { + internalDragAction->previewOption.badgeNumber = dragAction->dragPreviewOption.badgeNumber; + } else { + internalDragAction->previewOption.isShowBadge = dragAction->dragPreviewOption.isShowBadge; + } + RefPtr udData = UdmfClient::GetInstance()->TransformUnifiedDataForNative(dragAction->unifiedData); + internalDragAction->unifiedData = udData; + internalDragAction->instanceId = dragAction->instanceId; + internalDragAction->touchPointX = dragAction->touchPointX; + internalDragAction->touchPointY = dragAction->touchPointY; + internalDragAction->hasTouchPoint = dragAction->hasTouchPoint; +} + +ArkUI_Int32 StartDrag(ArkUIDragAction* dragAction) +{ + CHECK_NULL_RETURN(dragAction, -1); + auto internalDragAction = std::make_shared(); + + CHECK_NULL_RETURN(internalDragAction, -1); + auto callbacks = [listener = dragAction->listener, userData = dragAction->userData, + instanceId = dragAction->instanceId](const DragNotifyMsg& dragNotifyMsg, int32_t status) { + auto pipelineContext = NG::PipelineContext::GetContextByContainerId(instanceId); + CHECK_NULL_VOID(pipelineContext); + auto manager = pipelineContext->GetDragDropManager(); + CHECK_NULL_VOID(manager); + ArkUIDragEvent dragEvent; + dragEvent.dragResult = static_cast(dragNotifyMsg.result); + dragEvent.dragBehavior = static_cast(dragNotifyMsg.dragBehavior); + + auto action = manager->GetDragAction(); + if (action != nullptr) { + action->hasHandle = false; + } + ArkUIDragAndDropInfo outInfo; + outInfo.status = status; + outInfo.dragEvent = &dragEvent; + CHECK_NULL_VOID(listener); + listener(&outInfo, userData); + }; + internalDragAction->callback = callbacks; + DragActionConvert(dragAction, internalDragAction); + OHOS::Ace::NG::DragDropFuncWrapper::StartDragAction(internalDragAction); + return 0; +} + +void RegisterStatusListener(ArkUIDragAction* dragAction, void* userData, DragStatusCallback listener) +{ + CHECK_NULL_VOID(dragAction); + dragAction->listener = listener; + dragAction->userData = userData; +} + +void UnRegisterStatusListener(ArkUIDragAction* dragAction) +{ + CHECK_NULL_VOID(dragAction); + dragAction->listener = nullptr; + dragAction->userData = nullptr; +} + +ArkUIDragAction* CreateDragActionWithNode(ArkUINodeHandle node) +{ + auto* dragAction = new ArkUIDragAction(); + CHECK_NULL_RETURN(node, nullptr); + auto* frameNode = reinterpret_cast(node); + CHECK_NULL_RETURN(frameNode, nullptr); + auto pipeline = frameNode->GetContext(); + CHECK_NULL_RETURN(pipeline, nullptr); + dragAction->instanceId = pipeline->GetInstanceId(); + return dragAction; +} + +ArkUIDragAction* CreateDragActionWithContext(ArkUIContext* context) +{ + auto* dragAction = new ArkUIDragAction(); + CHECK_NULL_RETURN(context, nullptr); + dragAction->instanceId = context->id; + return dragAction; +} void SetDragPreview(ArkUINodeHandle node, void* dragPreview) { @@ -40,15 +145,12 @@ void SetDragEventStrictReportingEnabledWithContext(ArkUI_Int32 instanceId, bool { NG::ViewAbstract::SetDragEventStrictReportingEnabled(instanceId, enabled); } - } // namespace const ArkUIDragAdapterAPI* GetDragAdapterAPI() { - static const ArkUIDragAdapterAPI impl { - SetDragPreview, - SetDragEventStrictReportingEnabledWithNode, - SetDragEventStrictReportingEnabledWithContext - }; + static const ArkUIDragAdapterAPI impl { StartDrag, RegisterStatusListener, UnRegisterStatusListener, + CreateDragActionWithNode, CreateDragActionWithContext, SetDragPreview, + SetDragEventStrictReportingEnabledWithNode, SetDragEventStrictReportingEnabledWithContext }; return &impl; } -} // namespace OHOS::Ace::DragAdapter \ No newline at end of file +} // namespace OHOS::Ace::DragAdapter diff --git a/frameworks/core/interfaces/native/node/drag_adapter_impl.h b/frameworks/core/interfaces/native/node/drag_adapter_impl.h index 53e1d0512fb..8b2915ea2a0 100644 --- a/frameworks/core/interfaces/native/node/drag_adapter_impl.h +++ b/frameworks/core/interfaces/native/node/drag_adapter_impl.h @@ -13,8 +13,9 @@ * limitations under the License. */ -#ifndef FRAMEWORKS_INTERFACE_INNER_API_NATIVE_NODED_DRAG_ADAPTER_IMPL_H -#define FRAMEWORKS_INTERFACE_INNER_API_NATIVE_NODED_DRAG_ADAPTER_IMPL_H +#ifndef FRAMEWORKS_INTERFACE_INNER_API_NATIVE_NODE_DRAG_ADAPTER_IMPL_H +#define FRAMEWORKS_INTERFACE_INNER_API_NATIVE_NODE_DRAG_ADAPTER_IMPL_H +#pragma once #include #include @@ -27,8 +28,7 @@ #include "core/components_ng/base/ui_node.h" #include "core/interfaces/arkoala/arkoala_api.h" - namespace OHOS::Ace::DragAdapter { const ArkUIDragAdapterAPI* GetDragAdapterAPI(); } // namespace OHOS::Ace::DragAdapter -#endif // FRAMEWORKS_INTERFACE_INNER_API_NATIVE_NODED_DRAG_ADAPTER_IMPL_H \ No newline at end of file +#endif diff --git a/frameworks/core/interfaces/native/node/node_api.cpp b/frameworks/core/interfaces/native/node/node_api.cpp index b4e12954c8e..1d6aedf5d7a 100644 --- a/frameworks/core/interfaces/native/node/node_api.cpp +++ b/frameworks/core/interfaces/native/node/node_api.cpp @@ -64,6 +64,7 @@ #include "core/interfaces/native/node/view_model.h" #include "core/interfaces/native/node/water_flow_modifier.h" #include "core/pipeline_ng/pipeline_context.h" +#include "core/interfaces/native/node/drag_adapter_impl.h" namespace OHOS::Ace::NG { namespace { diff --git a/interfaces/native/event/drag_and_drop_impl.cpp b/interfaces/native/event/drag_and_drop_impl.cpp index a7184eb0346..999c11aec83 100644 --- a/interfaces/native/event/drag_and_drop_impl.cpp +++ b/interfaces/native/event/drag_and_drop_impl.cpp @@ -20,7 +20,7 @@ #include "ndk_data_conversion.h" #include "pixelmap_native_impl.h" #include "securec.h" - +#include #include "base/error/error_code.h" #include "base/log/log_wrapper.h" #include "core/interfaces/arkoala/arkoala_api.h" @@ -28,6 +28,7 @@ #include "frameworks/core/common/ace_engine.h" #include "frameworks/core/common/container.h" #include "frameworks/core/interfaces/native/node/node_api.h" +#include "base/utils/utils.h" #ifdef __cplusplus extern "C" { @@ -108,6 +109,184 @@ int32_t OH_ArkUI_DragEvent_GetDataTypes( } return ARKUI_ERROR_CODE_NO_ERROR; } +ArkUI_DragAction* OH_ArkUI_CreateDragActionWithNode(ArkUI_NodeHandle node) +{ + auto* impl = OHOS::Ace::NodeModel::GetFullImpl(); + if (!impl || !node) { + return nullptr; + } + auto dragActions = impl->getDragAdapterAPI()->createDragActionWithNode(node->uiNodeHandle); + return reinterpret_cast(dragActions); +} + +ArkUI_DragAction* OH_ArkUI_CreateDragActionWithContext(ArkUI_ContextHandle uiContext) +{ + auto* impl = OHOS::Ace::NodeModel::GetFullImpl(); + if (!impl || !uiContext) { + return nullptr; + } + auto* context = reinterpret_cast(uiContext); + auto dragActions = impl->getDragAdapterAPI()->createDragActionWithContext(context); + return reinterpret_cast(dragActions); +} + +void OH_ArkUI_DragAction_Dispose(ArkUI_DragAction* dragAction) +{ + if (!dragAction) { + return; + } + delete reinterpret_cast(dragAction); + dragAction = nullptr; +} + +int32_t OH_ArkUI_DragAction_SetPointerId(ArkUI_DragAction* dragAction, int32_t pointer) +{ + if (!dragAction) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + auto* dragActions = reinterpret_cast(dragAction); + if (!dragActions) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + if (pointer > 9 || pointer < 0) { + dragActions->pointerId = -1; + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + dragActions->pointerId = pointer; + return ARKUI_ERROR_CODE_NO_ERROR; +} + +int32_t OH_ArkUI_DragAction_SetPixelMaps(ArkUI_DragAction* dragAction, OH_PixelmapNative* pixelmapArray[], int32_t size) +{ + if (!dragAction) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + auto* dragActions = reinterpret_cast(dragAction); + if (!dragActions) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + std::vector> pixelMapList; + for (int32_t index = 0; index < size; index++) { + if (!pixelmapArray[index]) { + continue; + } + pixelMapList.push_back(pixelmapArray[index]->GetInnerPixelmap()); + } + dragActions->pixelmapArray = reinterpret_cast(pixelMapList.data()); + dragActions->size = size; + return ARKUI_ERROR_CODE_NO_ERROR; +} + +int32_t OH_ArkUI_DragAction_SetTouchPointX(ArkUI_DragAction* dragAction, float x) +{ + if (!dragAction) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + auto* dragActions = reinterpret_cast(dragAction); + if (!dragActions) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + dragActions->touchPointX = x; + dragActions->hasTouchPoint = true; + return ARKUI_ERROR_CODE_NO_ERROR; +} + +int32_t OH_ArkUI_DragAction_SetTouchPointY(ArkUI_DragAction* dragAction, float y) +{ + if (!dragAction) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + auto* dragActions = reinterpret_cast(dragAction); + if (!dragActions) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + dragActions->touchPointY = y; + dragActions->hasTouchPoint = true; + return ARKUI_ERROR_CODE_NO_ERROR; +} + +int32_t OH_ArkUI_DragAction_SetData(ArkUI_DragAction* dragAction, OH_UdmfData* data) +{ + if (!dragAction || !data) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + auto* dragActions = reinterpret_cast(dragAction); + dragActions->unifiedData = data; + return ARKUI_ERROR_CODE_NO_ERROR; +} + +int32_t OH_ArkUI_DragAction_SetDragPreviewOption(ArkUI_DragAction* dragAction, ArkUI_DragPreviewOption* option) +{ + if (!dragAction || !option) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + auto* dragActions = reinterpret_cast(dragAction); + auto* options = reinterpret_cast(option); + if (!dragActions || !options) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + dragActions->dragPreviewOption = *options; + return ARKUI_ERROR_CODE_NO_ERROR; +} + +int32_t OH_ArkUI_DragAction_RegisterStatusListener(ArkUI_DragAction* dragAction, void* userData, + void (*listener)(ArkUI_DragAndDropInfo* dragAndDropInfo, void* userData)) +{ + auto* impl = OHOS::Ace::NodeModel::GetFullImpl(); + if (!impl || !dragAction) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + impl->getDragAdapterAPI()->registerStatusListener( + reinterpret_cast(dragAction), userData, (reinterpret_cast(listener))); + return ARKUI_ERROR_CODE_NO_ERROR; +} + +void OH_ArkUI_DragAction_UnregisterStatusListener(ArkUI_DragAction* dragAction) +{ + auto* impl = OHOS::Ace::NodeModel::GetFullImpl(); + if (!impl || !dragAction) { + return; + } + impl->getDragAdapterAPI()->unregisterStatusListener(reinterpret_cast(dragAction)); +} + +ArkUI_DragStatus OH_ArkUI_DragAndDropInfo_GetDragStatus(ArkUI_DragAndDropInfo* dragAndDropInfo) +{ + if (!dragAndDropInfo) { + return ArkUI_DragStatus::ARKUI_DRAG_STATUS_UNKNOWN; + } + auto* dragAndDropInfos = reinterpret_cast(dragAndDropInfo); + if (!dragAndDropInfos) { + return ArkUI_DragStatus::ARKUI_DRAG_STATUS_UNKNOWN; + } + return static_cast(dragAndDropInfos->status); +} + +ArkUI_DragEvent* OH_ArkUI_DragAndDropInfo_GetDragEvent(ArkUI_DragAndDropInfo* dragAndDropInfo) +{ + if (!dragAndDropInfo) { + return nullptr; + } + auto* dragAndDropInfos = reinterpret_cast(dragAndDropInfo); + if (!dragAndDropInfos) { + return nullptr; + } + return reinterpret_cast(dragAndDropInfos->dragEvent); +} + +int32_t OH_ArkUI_StartDrag(ArkUI_DragAction* dragAction) +{ + if (!dragAction) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + auto* dragActions = reinterpret_cast(dragAction); + auto* impl = OHOS::Ace::NodeModel::GetFullImpl(); + if (!dragActions || !impl) { + return ARKUI_ERROR_CODE_PARAM_INVALID; + } + impl->getDragAdapterAPI()->startDrag(dragActions); + return ARKUI_ERROR_CODE_NO_ERROR; +} ArkUI_PreviewDragStatus OH_ArkUI_NodeEvent_GetPreviewDragStatus(ArkUI_NodeEvent* nodeEvent) { -- Gitee