1 /*
2 * Copyright (c) 2022-2024 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "core/components_ng/manager/drag_drop/drag_drop_manager.h"
17
18 #include "base/geometry/ng/offset_t.h"
19 #include "base/geometry/point.h"
20 #include "base/subwindow/subwindow_manager.h"
21 #include "base/geometry/rect.h"
22 #include "base/log/ace_trace.h"
23 #include "base/utils/system_properties.h"
24 #include "base/utils/time_util.h"
25 #include "base/utils/utils.h"
26 #include "core/common/interaction/interaction_data.h"
27 #include "core/common/interaction/interaction_interface.h"
28 #include "core/common/udmf/udmf_client.h"
29 #include "core/components/common/layout/grid_column_info.h"
30 #include "core/components_ng/manager/drag_drop/drag_drop_behavior_reporter/drag_drop_behavior_reporter.h"
31 #include "core/components/common/layout/grid_system_manager.h"
32 #include "core/components_ng/base/frame_node.h"
33 #include "core/components_ng/pattern/grid/grid_event_hub.h"
34 #include "core/components_ng/pattern/list/list_event_hub.h"
35 #include "core/components_ng/pattern/menu/wrapper/menu_wrapper_pattern.h"
36 #include "core/components_ng/pattern/root/root_pattern.h"
37 #include "core/components_ng/pattern/text_field/text_field_pattern.h"
38 #include "core/components_v2/inspector/inspector_constants.h"
39 #include "core/pipeline_ng/pipeline_context.h"
40
41 namespace OHOS::Ace::NG {
42 namespace {
43 int64_t g_proxyId = 0;
44 constexpr int32_t MAX_RETRY_TIMES = 3;
45 constexpr int32_t MAX_RETRY_DURATION = 800;
46 constexpr float MOVE_DISTANCE_LIMIT = 20.0f;
47 constexpr uint64_t MOVE_TIME_LIMIT = 6L;
48 constexpr Dimension PRESERVE_HEIGHT = 8.0_vp;
49 constexpr float FIRST_PIXELMAP_OPACITY = 0.6f;
50 constexpr float SECOND_PIXELMAP_OPACITY = 0.3f;
51 constexpr float FIRST_PIXELMAP_ANGLE = 8.0f;
52 constexpr float SECOND_PIXELMAP_ANGLE = -8.0f;
53 constexpr int32_t FIRST_GATHER_PIXEL_MAP = 1;
54 constexpr int32_t SECOND_GATHER_PIXEL_MAP = 2;
55 constexpr int32_t SQUARE_NUMBER = 2;
56 constexpr float TOUCH_DRAG_PIXELMAP_SCALE = 1.05f;
57 constexpr float MAX_DISTANCE_TO_PRE_POINTER = 3.0f;
58 constexpr float DEFAULT_SPRING_RESPONSE = 0.347f;
59 constexpr float MIN_SPRING_RESPONSE = 0.05f;
60 constexpr float DEL_SPRING_RESPONSE = 0.005f;
61 constexpr int32_t RESERVED_DEVICEID_1 = 0xAAAAAAFF;
62 constexpr int32_t RESERVED_DEVICEID_2 = 0xAAAAAAFE;
63 } // namespace
64
GetMenuRenderContextFromMenuWrapper(const RefPtr<FrameNode> & menuWrapperNode)65 RefPtr<RenderContext> GetMenuRenderContextFromMenuWrapper(const RefPtr<FrameNode>& menuWrapperNode)
66 {
67 CHECK_NULL_RETURN(menuWrapperNode, nullptr);
68 auto menuWrapperPattern = menuWrapperNode->GetPattern<MenuWrapperPattern>();
69 CHECK_NULL_RETURN(menuWrapperPattern, nullptr);
70 auto menuNode = menuWrapperPattern->GetMenu();
71 CHECK_NULL_RETURN(menuNode, nullptr);
72 return menuNode->GetRenderContext();
73 }
74
GetMenuWrapperNodeFromDrag()75 RefPtr<FrameNode> GetMenuWrapperNodeFromDrag()
76 {
77 auto pipeline = PipelineContext::GetMainPipelineContext();
78 CHECK_NULL_RETURN(pipeline, nullptr);
79 auto dragDropManager = pipeline->GetDragDropManager();
80 CHECK_NULL_RETURN(dragDropManager, nullptr);
81 return dragDropManager->GetMenuWrapperNode();
82 }
83
CreateAndShowItemDragOverlay(const RefPtr<PixelMap> & pixelMap,const GestureEvent & info,const RefPtr<EventHub> & eventHub)84 RefPtr<DragDropProxy> DragDropManager::CreateAndShowItemDragOverlay(
85 const RefPtr<PixelMap>& pixelMap, const GestureEvent& info, const RefPtr<EventHub>& eventHub)
86 {
87 CHECK_NULL_RETURN(pixelMap, nullptr);
88 // create Image for drag
89 auto imageNode = FrameNode::GetOrCreateFrameNode(V2::IMAGE_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
90 []() { return AceType::MakeRefPtr<ImagePattern>(); });
91 CHECK_NULL_RETURN(imageNode, nullptr);
92 auto imagePattern = imageNode->GetPattern<ImagePattern>();
93 CHECK_NULL_RETURN(imagePattern, nullptr);
94 imagePattern->SetSyncLoad(true);
95 auto prop = imageNode->GetLayoutProperty<ImageLayoutProperty>();
96 CHECK_NULL_RETURN(prop, nullptr);
97 prop->UpdateAutoResize(false);
98 prop->UpdateImageSourceInfo(ImageSourceInfo(pixelMap));
99 auto targetSize = CalcSize(NG::CalcLength(pixelMap->GetWidth()), NG::CalcLength(pixelMap->GetHeight()));
100 prop->UpdateUserDefinedIdealSize(targetSize);
101 auto renderProp = imageNode->GetPaintProperty<ImageRenderProperty>();
102 renderProp->UpdateImageInterpolation(ImageInterpolation::HIGH);
103 imageNode->MarkDirtyNode(NG::PROPERTY_UPDATE_MEASURE);
104 imageNode->MarkModifyDone();
105 imageNode->SetLayoutDirtyMarked(true);
106 imageNode->SetActive(true);
107 imageNode->CreateLayoutTask();
108 auto imageContext = imageNode->GetRenderContext();
109 CHECK_NULL_RETURN(imageContext, nullptr);
110 imageContext->UpdatePosition(
111 OffsetT<Dimension>(Dimension(info.GetGlobalPoint().GetX() - pixelMap->GetWidth() / 2), // 2: Average factor.
112 Dimension(info.GetGlobalPoint().GetY() - pixelMap->GetHeight() / 2))); // 2: Average factor.
113 imageContext->OnModifyDone();
114
115 AddItemDrag(imageNode, eventHub);
116
117 itemDragOverlayNode_ = imageNode;
118 SetIsDragged(true);
119 isDragCancel_ = false;
120 currentId_ = ++g_proxyId;
121 return MakeRefPtr<DragDropProxy>(currentId_);
122 }
123
CreateAndShowItemDragOverlay(const RefPtr<UINode> & customNode,const GestureEvent & info,const RefPtr<EventHub> & eventHub)124 RefPtr<DragDropProxy> DragDropManager::CreateAndShowItemDragOverlay(
125 const RefPtr<UINode>& customNode, const GestureEvent& info, const RefPtr<EventHub>& eventHub)
126 {
127 auto frameNode = DynamicCast<FrameNode>(customNode);
128 CHECK_NULL_RETURN(frameNode, nullptr);
129 auto renderContext = frameNode->GetRenderContext();
130 CHECK_NULL_RETURN(renderContext, nullptr);
131 auto geometryNode = frameNode->GetGeometryNode();
132 CHECK_NULL_RETURN(geometryNode, nullptr);
133 auto frameRect = geometryNode->GetFrameSize();
134 renderContext->UpdatePosition(
135 OffsetT<Dimension>(Dimension(info.GetGlobalPoint().GetX() - frameRect.Width() / 2), // 2: Average factor.
136 Dimension(info.GetGlobalPoint().GetY() - frameRect.Height() / 2))); // 2: Average factor.
137 renderContext->OnModifyDone();
138 AddItemDrag(frameNode, eventHub);
139 itemDragOverlayNode_ = frameNode;
140 SetIsDragged(true);
141 isDragCancel_ = false;
142 currentId_ = ++g_proxyId;
143 return MakeRefPtr<DragDropProxy>(currentId_);
144 }
145
CreateTextDragDropProxy()146 RefPtr<DragDropProxy> DragDropManager::CreateTextDragDropProxy()
147 {
148 SetIsDragged(true);
149 isDragCancel_ = false;
150 currentId_ = ++g_proxyId;
151 return MakeRefPtr<DragDropProxy>(currentId_);
152 }
153
GetWindowId()154 int32_t DragDropManager::GetWindowId()
155 {
156 auto windowId = -1;
157 auto container = Container::Current();
158 CHECK_NULL_RETURN(container, windowId);
159
160 if (!container->IsSceneBoardEnabled()) {
161 isDragWindowSubWindow_ = false;
162 return windowId;
163 }
164
165 if (!container->IsMainWindow()) {
166 // The window manager currently does not support creating child windows within child windows,
167 // so the root main window is used here
168 container = Container::GetContainer(CONTAINER_ID_DIVIDE_SIZE);
169 CHECK_NULL_RETURN(container, windowId);
170 if (!container->IsMainWindow()) {
171 isDragWindowSubWindow_ = false;
172 return windowId;
173 }
174 }
175
176 windowId = static_cast<int32_t>(container->GetWindowId());
177 isDragWindowSubWindow_ = true;
178
179 return windowId;
180 }
181
CreateDragRootNode(const RefPtr<UINode> & customNode)182 RefPtr<FrameNode> DragDropManager::CreateDragRootNode(const RefPtr<UINode>& customNode)
183 {
184 auto pipeline = PipelineContext::GetCurrentContext();
185 CHECK_NULL_RETURN(pipeline, nullptr);
186
187 auto rootNode = FrameNode::CreateFrameNodeWithTree(
188 V2::ROOT_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(), MakeRefPtr<RootPattern>());
189 rootNode->SetActive(true);
190 rootNode->SetHostRootId(pipeline->GetInstanceId());
191 rootNode->SetHostPageId(-1);
192 rootNode->AddChild(customNode);
193 rootNode->AttachToMainTree(false, AceType::RawPtr(pipeline));
194 rootNode->MarkDirtyNode(PROPERTY_UPDATE_MEASURE);
195 pipeline->FlushUITasks();
196 return rootNode;
197 }
198
AddItemDrag(const RefPtr<FrameNode> & frameNode,const RefPtr<EventHub> & eventHub)199 void DragDropManager::AddItemDrag(const RefPtr<FrameNode>& frameNode, const RefPtr<EventHub>& eventHub)
200 {
201 auto pipeline = frameNode->GetContext();
202 CHECK_NULL_VOID(pipeline);
203 auto rootNode = pipeline->GetRootElement();
204 auto container = Container::Current();
205 if (container && container->IsScenceBoardWindow()) {
206 auto host = eventHub->GetFrameNode();
207 CHECK_NULL_VOID(host);
208 auto overlayManager = pipeline->GetOverlayManager();
209 CHECK_NULL_VOID(overlayManager);
210 rootNode = DynamicCast<FrameNode>(overlayManager->FindWindowScene(host));
211 }
212 CHECK_NULL_VOID(rootNode);
213 frameNode->MountToParent(rootNode);
214 frameNode->OnMountToParentDone();
215 rootNode->MarkDirtyNode(PROPERTY_UPDATE_BY_CHILD_REQUEST);
216 }
217
RemoveItemDrag()218 void DragDropManager::RemoveItemDrag()
219 {
220 CHECK_NULL_VOID(itemDragOverlayNode_);
221 auto rootNode = itemDragOverlayNode_->GetParent();
222 CHECK_NULL_VOID(rootNode);
223 rootNode->RemoveChild(itemDragOverlayNode_);
224 rootNode->RebuildRenderContextTree();
225 rootNode->MarkDirtyNode(PROPERTY_UPDATE_BY_CHILD_REQUEST);
226 }
227
UpdateItemDragPosition(int32_t globalX,int32_t globalY)228 void DragDropManager::UpdateItemDragPosition(int32_t globalX, int32_t globalY)
229 {
230 CHECK_NULL_VOID(itemDragOverlayNode_);
231 auto rect = itemDragOverlayNode_->GetTransformRectRelativeToWindow();
232 auto pipeline = itemDragOverlayNode_->GetContext();
233 CHECK_NULL_VOID(pipeline);
234 const Rect windowRect = pipeline->GetDisplayWindowRectInfo();
235 auto maxX = static_cast<float>(windowRect.Width() - rect.Width());
236 auto maxY = static_cast<float>(windowRect.Height() - rect.Height());
237 auto renderContext = itemDragOverlayNode_->GetRenderContext();
238 CHECK_NULL_VOID(renderContext);
239 renderContext->UpdatePosition(
240 OffsetT<Dimension>(Dimension(std::min(std::max(globalX - rect.Width() / 2, 0.0f), maxX)), // 2: Average factor.
241 Dimension(std::min(std::max(globalY - rect.Height() / 2, 0.0f), maxY)))); // 2: Average factor.
242 renderContext->OnModifyDone();
243 }
244
HideDragPreviewOverlay()245 void DragDropManager::HideDragPreviewOverlay()
246 {
247 auto pipeline = NG::PipelineContext::GetCurrentContext();
248 CHECK_NULL_VOID(pipeline);
249 auto manager = pipeline->GetOverlayManager();
250 CHECK_NULL_VOID(manager);
251 manager->RemovePixelMap();
252 manager->RemoveGatherNode();
253 manager->RemoveDragPixelMap();
254 SubwindowManager::GetInstance()->HidePreviewNG();
255 }
256
HideDragPreviewWindow(int32_t containerId)257 void DragDropManager::HideDragPreviewWindow(int32_t containerId)
258 {
259 auto overlayManager = GetDragAnimationOverlayManager(containerId);
260 CHECK_NULL_VOID(overlayManager);
261 overlayManager->RemovePixelMap();
262 overlayManager->RemoveGatherNode();
263 overlayManager->RemoveDragPixelMap();
264 SubwindowManager::GetInstance()->HidePreviewNG();
265 }
266
FindTargetInChildNodes(const RefPtr<UINode> parentNode,std::vector<RefPtr<FrameNode>> hitFrameNodes,bool findDrop)267 RefPtr<FrameNode> DragDropManager::FindTargetInChildNodes(
268 const RefPtr<UINode> parentNode, std::vector<RefPtr<FrameNode>> hitFrameNodes, bool findDrop)
269 {
270 CHECK_NULL_RETURN(parentNode, nullptr);
271 auto parentFrameNode = AceType::DynamicCast<FrameNode>(parentNode);
272 if (parentFrameNode && (!parentFrameNode->IsActive() || !parentFrameNode->IsVisible())) {
273 return nullptr;
274 }
275 auto children = parentFrameNode->GetFrameChildren();
276
277 for (auto iter = children.rbegin(); iter != children.rend(); iter++) {
278 auto child = iter->Upgrade();
279 if (child == nullptr) {
280 continue;
281 }
282 auto childNode = AceType::DynamicCast<UINode>(child);
283 auto childFindResult = FindTargetInChildNodes(childNode, hitFrameNodes, findDrop);
284 if (childFindResult) {
285 return childFindResult;
286 }
287 }
288
289 CHECK_NULL_RETURN(parentFrameNode, nullptr);
290 for (auto iter : hitFrameNodes) {
291 if (parentFrameNode == iter) {
292 auto eventHub = parentFrameNode->GetEventHub<EventHub>();
293 if (!eventHub) {
294 continue;
295 }
296 if ((eventHub->HasOnDrop()) || (eventHub->HasOnItemDrop()) || (eventHub->HasCustomerOnDrop())) {
297 return parentFrameNode;
298 }
299 if ((V2::UI_EXTENSION_COMPONENT_ETS_TAG == parentFrameNode->GetTag() ||
300 V2::EMBEDDED_COMPONENT_ETS_TAG == parentFrameNode->GetTag()) &&
301 (!IsUIExtensionShowPlaceholder(parentFrameNode))) {
302 return parentFrameNode;
303 }
304 }
305 }
306 return nullptr;
307 }
308
CheckFrameNodeCanDrop(const RefPtr<FrameNode> & node)309 bool DragDropManager::CheckFrameNodeCanDrop(const RefPtr<FrameNode>& node)
310 {
311 CHECK_NULL_RETURN(node, false);
312 auto eventHub = node->GetEventHub<EventHub>();
313 CHECK_NULL_RETURN(eventHub, false);
314 if ((eventHub->HasOnDrop()) || (eventHub->HasOnItemDrop()) || (eventHub->HasCustomerOnDrop())) {
315 return true;
316 }
317 if ((V2::UI_EXTENSION_COMPONENT_ETS_TAG == node->GetTag() ||
318 V2::EMBEDDED_COMPONENT_ETS_TAG == node->GetTag()) &&
319 (!IsUIExtensionShowPlaceholder(node))) {
320 return true;
321 }
322
323 return false;
324 }
325
FindTargetDropNode(const RefPtr<UINode> parentNode,PointF localPoint)326 RefPtr<FrameNode> DragDropManager::FindTargetDropNode(const RefPtr<UINode> parentNode, PointF localPoint)
327 {
328 CHECK_NULL_RETURN(parentNode, nullptr);
329 auto parentFrameNode = AceType::DynamicCast<FrameNode>(parentNode);
330 CHECK_NULL_RETURN(parentFrameNode, nullptr);
331 if (!parentFrameNode->IsActive() || !parentFrameNode->IsVisible()) {
332 return nullptr;
333 }
334 auto renderContext = parentFrameNode->GetRenderContext();
335 CHECK_NULL_RETURN(renderContext, nullptr);
336 auto paintRect = renderContext->GetPaintRectWithoutTransform();
337 FrameNode::MapPointTo(localPoint, parentFrameNode->GetOrRefreshRevertMatrixFromCache());
338 auto subLocalPoint = localPoint - paintRect.GetOffset();
339
340 auto children = parentFrameNode->GetFrameChildren();
341 for (auto iter = children.rbegin(); iter != children.rend(); iter++) {
342 auto child = iter->Upgrade();
343 if (child == nullptr) {
344 continue;
345 }
346 auto childNode = AceType::DynamicCast<UINode>(child);
347 auto childFindResult = FindTargetDropNode(childNode, subLocalPoint);
348 if (childFindResult) {
349 return childFindResult;
350 }
351 }
352
353 if (paintRect.IsInRegion(localPoint)) {
354 if (parentFrameNode->GetDragHitTestBlock()) {
355 return parentFrameNode;
356 }
357 if (CheckFrameNodeCanDrop(parentFrameNode)) {
358 return parentFrameNode;
359 }
360 }
361 return nullptr;
362 }
363
FindDragFrameNodeByPosition(float globalX,float globalY,const RefPtr<FrameNode> & node)364 RefPtr<FrameNode> DragDropManager::FindDragFrameNodeByPosition(float globalX, float globalY,
365 const RefPtr<FrameNode>& node)
366 {
367 auto rootNode = node;
368 if (!rootNode) {
369 auto pipeline = NG::PipelineContext::GetCurrentContext();
370 CHECK_NULL_RETURN(pipeline, nullptr);
371 rootNode = pipeline->GetRootElement();
372 }
373
374 auto result = FindTargetDropNode(rootNode, {globalX, globalY});
375 if (result) {
376 if (CheckFrameNodeCanDrop(result)) {
377 return result;
378 }
379 }
380 return nullptr;
381 }
382
CheckDragDropProxy(int64_t id) const383 bool DragDropManager::CheckDragDropProxy(int64_t id) const
384 {
385 return currentId_ == id;
386 }
387
UpdateDragAllowDrop(const RefPtr<FrameNode> & dragFrameNode,const DragBehavior dragBehavior,const int32_t eventId,bool isCapi)388 void DragDropManager::UpdateDragAllowDrop(
389 const RefPtr<FrameNode>& dragFrameNode, const DragBehavior dragBehavior, const int32_t eventId, bool isCapi)
390 {
391 if (!IsDropAllowed(dragFrameNode)) {
392 // simplified specifications for drag cursor style, no longer showing forbidden drag cursor
393 UpdateDragStyle(DragCursorStyleCore::MOVE, eventId);
394 return;
395 }
396
397 // drop allowed
398 CHECK_NULL_VOID(dragFrameNode);
399 const auto& dragFrameNodeAllowDrop = dragFrameNode->GetAllowDrop();
400 // special handling for no drag data present situation, always show as move
401 // For CAPI ,no ENABLE_DROP and DISABLE_DROP state, skip the judgment and consider it allowed to drop into. Continue
402 // to set dragBehavior.
403 if (!isCapi && (dragFrameNodeAllowDrop.empty() || summaryMap_.empty())) {
404 UpdateDragStyle(DragCursorStyleCore::MOVE, eventId);
405 return;
406 }
407
408 //other case, check drag behavior
409 switch (dragBehavior) {
410 case DragBehavior::UNKNOWN: {
411 // the application does not config the drag behavior, use move when moving within
412 // draggedFrameNode or frameNode is disabled, otherwise use copy
413 auto eventHub = dragFrameNode->GetEventHub<EventHub>();
414 if (draggedFrameNode_ == dragFrameNode || !(eventHub && eventHub->IsEnabled()) ||
415 CheckExtraSituation(dragFrameNode)) {
416 UpdateDragStyle(DragCursorStyleCore::MOVE, eventId);
417 } else {
418 UpdateDragStyle(DragCursorStyleCore::COPY, eventId);
419 }
420 break;
421 }
422 case DragBehavior::MOVE: {
423 UpdateDragStyle(DragCursorStyleCore::MOVE, eventId);
424 break;
425 }
426 case DragBehavior::COPY: {
427 UpdateDragStyle(DragCursorStyleCore::COPY, eventId);
428 break;
429 }
430 default: {
431 UpdateDragStyle(DragCursorStyleCore::COPY, eventId);
432 break;
433 }
434 }
435 }
436
CheckExtraSituation(const RefPtr<FrameNode> & dragFrameNode) const437 bool DragDropManager::CheckExtraSituation(const RefPtr<FrameNode>& dragFrameNode) const
438 {
439 return CheckInRichEditor(dragFrameNode);
440 }
441
CheckInRichEditor(const RefPtr<FrameNode> & dragFrameNode) const442 bool DragDropManager::CheckInRichEditor(const RefPtr<FrameNode>& dragFrameNode) const
443 {
444 CHECK_NULL_RETURN(dragFrameNode && draggedFrameNode_, false);
445 auto parent = draggedFrameNode_->GetAncestorNodeOfFrame(false);
446 CHECK_NULL_RETURN(parent && parent->GetTag() == V2::RICH_EDITOR_ETS_TAG, false);
447 return dragFrameNode == parent;
448 }
449
UpdateDragStyle(const DragCursorStyleCore & dragStyle,int32_t eventId)450 void DragDropManager::UpdateDragStyle(const DragCursorStyleCore& dragStyle, int32_t eventId)
451 {
452 if (dragStyle != dragCursorStyleCore_) {
453 TAG_LOGI(
454 AceLogTag::ACE_DRAG, "Update DragStyle to %{public}d, pointerEventId: %{public}d.", dragStyle, eventId);
455 auto ret = InteractionInterface::GetInstance()->UpdateDragStyle(dragStyle, eventId);
456 if (ret != 0) {
457 TAG_LOGI(AceLogTag::ACE_DRAG,
458 "Update DragStyle to %{public}d failed, keep %{public}d. pointerEventId: %{public}d. ret = %{public}d",
459 dragStyle, dragCursorStyleCore_, eventId, ret);
460 } else {
461 dragCursorStyleCore_ = dragStyle;
462 }
463 }
464 }
465
CheckParentVisible(const RefPtr<FrameNode> & frameNode)466 bool CheckParentVisible(const RefPtr<FrameNode>& frameNode)
467 {
468 bool isVisible = frameNode->IsVisible();
469 if (!isVisible) {
470 return false;
471 }
472 auto parent = frameNode->GetParent();
473 while (parent && parent->GetDepth() != 1) {
474 auto parentFrameNode = AceType::DynamicCast<FrameNode>(parent);
475 if (parentFrameNode && !parentFrameNode->IsVisible()) {
476 isVisible = false;
477 break;
478 }
479 parent = parent->GetParent();
480 }
481 return isVisible;
482 }
483
FindHitFrameNodes(const Point & point)484 std::unordered_set<int32_t> DragDropManager::FindHitFrameNodes(const Point& point)
485 {
486 std::unordered_set<int32_t> frameNodeList;
487 for (auto iter = nodesForDragNotify_.begin(); iter != nodesForDragNotify_.end(); iter++) {
488 auto frameNode = iter->second.Upgrade();
489 if (!frameNode || !frameNode->IsActive() || !frameNode->IsVisible() || frameNode->GetDepth() < 0) {
490 continue;
491 }
492 auto geometryNode = frameNode->GetGeometryNode();
493 if (!geometryNode) {
494 continue;
495 }
496 auto globalFrameRect = geometryNode->GetFrameRect();
497 globalFrameRect.SetOffset(frameNode->GetTransformRelativeOffset());
498 if (globalFrameRect.IsInRegion(PointF(static_cast<float>(point.GetX()), static_cast<float>(point.GetY())))) {
499 frameNodeList.emplace(frameNode->GetId());
500 }
501 }
502 return frameNodeList;
503 }
504
UpdateDragListener(const Point & point)505 void DragDropManager::UpdateDragListener(const Point& point)
506 {
507 auto hitNodes = FindHitFrameNodes(point);
508 std::unordered_map<int32_t, WeakPtr<FrameNode>> dragEnterNodes;
509 std::unordered_map<int32_t, WeakPtr<FrameNode>> dragMoveNodes;
510 std::unordered_map<int32_t, WeakPtr<FrameNode>> dragLeaveNodes;
511 for (auto iter = nodesForDragNotify_.begin(); iter != nodesForDragNotify_.end(); iter++) {
512 auto localHitResult = hitNodes.find(iter->first) != hitNodes.end();
513 auto preHitResult = parentHitNodes_.find(iter->first) != parentHitNodes_.end();
514 if (localHitResult && preHitResult) {
515 dragMoveNodes[iter->first] = iter->second;
516 }
517 if (localHitResult && !preHitResult) {
518 dragEnterNodes[iter->first] = iter->second;
519 }
520 if (!localHitResult && preHitResult) {
521 dragLeaveNodes[iter->first] = iter->second;
522 }
523 }
524 RefPtr<NotifyDragEvent> notifyEvent = AceType::MakeRefPtr<NotifyDragEvent>();
525 UpdateNotifyDragEvent(notifyEvent, point, DragEventType::MOVE);
526
527 NotifyDragRegisterFrameNode(dragMoveNodes, DragEventType::MOVE, notifyEvent);
528 NotifyDragRegisterFrameNode(dragEnterNodes, DragEventType::ENTER, notifyEvent);
529 NotifyDragRegisterFrameNode(dragLeaveNodes, DragEventType::LEAVE, notifyEvent);
530 parentHitNodes_ = std::move(hitNodes);
531 }
532
NotifyDragRegisterFrameNode(std::unordered_map<int32_t,WeakPtr<FrameNode>> nodes,DragEventType dragEventType,RefPtr<NotifyDragEvent> & notifyEvent)533 void DragDropManager::NotifyDragRegisterFrameNode(std::unordered_map<int32_t, WeakPtr<FrameNode>> nodes,
534 DragEventType dragEventType, RefPtr<NotifyDragEvent>& notifyEvent)
535 {
536 for (auto iter = nodes.begin(); iter != nodes.end(); iter++) {
537 auto frameNode = iter->second.Upgrade();
538 if (!frameNode) {
539 continue;
540 }
541 auto eventHub = frameNode->GetEventHub<EventHub>();
542 if (!CheckParentVisible(frameNode) || (eventHub && !eventHub->IsEnabled())) {
543 continue;
544 }
545 auto pattern = frameNode->GetPattern<Pattern>();
546 if (!pattern) {
547 continue;
548 }
549 pattern->HandleOnDragStatusCallback(dragEventType, notifyEvent);
550 }
551 }
552
NotifyDragFrameNode(const Point & point,const DragEventType & dragEventType,const DragRet & dragRet)553 void DragDropManager::NotifyDragFrameNode(
554 const Point& point, const DragEventType& dragEventType, const DragRet& dragRet)
555 {
556 RefPtr<NotifyDragEvent> notifyEvent = AceType::MakeRefPtr<NotifyDragEvent>();
557 UpdateNotifyDragEvent(notifyEvent, point, dragEventType);
558 notifyEvent->SetResult(dragRet);
559 NotifyDragRegisterFrameNode(nodesForDragNotify_, dragEventType, notifyEvent);
560 }
561
OnDragStart(const Point & point,const RefPtr<FrameNode> & frameNode)562 void DragDropManager::OnDragStart(const Point& point, const RefPtr<FrameNode>& frameNode)
563 {
564 dragDropState_ = DragDropMgrState::DRAGGING;
565 NotifyDragFrameNode(point, DragEventType::START);
566 CHECK_NULL_VOID(frameNode);
567 preTargetFrameNode_ = frameNode;
568 draggedFrameNode_ = preTargetFrameNode_;
569 preMovePoint_ = point;
570 parentHitNodes_.emplace(frameNode->GetId());
571 }
572
OnDragStart(const Point & point)573 void DragDropManager::OnDragStart(const Point& point)
574 {
575 dragDropState_ = DragDropMgrState::DRAGGING;
576 NotifyDragFrameNode(point, DragEventType::START);
577 }
578
PrintDragFrameNode(const OHOS::Ace::DragPointerEvent & pointerEvent,const RefPtr<FrameNode> & dragFrameNode)579 void DragDropManager::PrintDragFrameNode(
580 const OHOS::Ace::DragPointerEvent& pointerEvent, const RefPtr<FrameNode>& dragFrameNode)
581 {
582 CHECK_NULL_VOID(dragFrameNode);
583 auto container = Container::Current();
584 CHECK_NULL_VOID(container);
585 if (preTargetFrameNode_) {
586 TAG_LOGI(AceLogTag::ACE_DRAG,
587 "Current windowId is %{public}d, pointerEventId is %{public}d, "
588 "PreTargetFrameNode is %{public}s, depth is %{public}d, New find "
589 "targetNode is %{public}s, depth is %{public}d.",
590 container->GetWindowId(), pointerEvent.pointerEventId, preTargetFrameNode_->GetTag().c_str(),
591 preTargetFrameNode_->GetDepth(), dragFrameNode->GetTag().c_str(), dragFrameNode->GetDepth());
592 } else {
593 TAG_LOGI(AceLogTag::ACE_DRAG,
594 "Current windowId is %{public}d, pointerEventId is %{public}d "
595 "PreTargetFrameNode is nullptr, New find targetNode is %{public}s, depth is %{public}d.",
596 container->GetWindowId(), pointerEvent.pointerEventId, dragFrameNode->GetTag().c_str(),
597 dragFrameNode->GetDepth());
598 }
599 }
600
PrintGridDragFrameNode(const float globalX,const float globalY,const RefPtr<FrameNode> & dragFrameNode)601 void DragDropManager::PrintGridDragFrameNode(
602 const float globalX, const float globalY, const RefPtr<FrameNode>& dragFrameNode)
603 {
604 CHECK_NULL_VOID(dragFrameNode);
605 auto container = Container::Current();
606 CHECK_NULL_VOID(container);
607 if (preGridTargetFrameNode_) {
608 TAG_LOGI(AceLogTag::ACE_DRAG,
609 "Current windowId is %{public}d,"
610 "PreTargetFrameNode is %{public}s, depth is %{public}d,"
611 "New find targetNode is %{public}s, depth is %{public}d.",
612 container->GetWindowId(), preGridTargetFrameNode_->GetTag().c_str(),
613 preGridTargetFrameNode_->GetDepth(), dragFrameNode->GetTag().c_str(), dragFrameNode->GetDepth());
614 } else {
615 TAG_LOGI(AceLogTag::ACE_DRAG,
616 "Current windowId is %{public}d, "
617 "PreTargetFrameNode is nullptr, New find targetNode is %{public}s, depth is %{public}d.",
618 container->GetWindowId(), dragFrameNode->GetTag().c_str(), dragFrameNode->GetDepth());
619 }
620 }
621
TransDragWindowToDragFwk(int32_t windowContainerId)622 void DragDropManager::TransDragWindowToDragFwk(int32_t windowContainerId)
623 {
624 if (isDragFwkShow_) {
625 return;
626 }
627 TAG_LOGI(AceLogTag::ACE_DRAG, "TransDragWindowToDragFwk is %{public}d", isDragFwkShow_);
628 InteractionInterface::GetInstance()->SetDragWindowVisible(true);
629 isDragFwkShow_ = true;
630 menuWrapperNode_ = nullptr;
631 auto overlayManager = GetDragAnimationOverlayManager(windowContainerId);
632 CHECK_NULL_VOID(overlayManager);
633 overlayManager->RemoveDragPixelMap();
634 overlayManager->RemoveGatherNode();
635 SubwindowManager::GetInstance()->HidePreviewNG();
636 info_.scale = -1.0;
637 dampingOverflowCount_ = 0;
638 }
639
OnDragMoveOut(const DragPointerEvent & pointerEvent)640 void DragDropManager::OnDragMoveOut(const DragPointerEvent& pointerEvent)
641 {
642 Point point = pointerEvent.GetPoint();
643 auto container = Container::Current();
644 if (container && container->IsScenceBoardWindow()) {
645 if (IsDragged() && IsWindowConsumed()) {
646 SetIsWindowConsumed(false);
647 return;
648 }
649 }
650 SetIsWindowConsumed(false);
651 UpdateVelocityTrackerPoint(point, false);
652 UpdateDragListener(Point(-1, -1));
653 if (preTargetFrameNode_) {
654 TAG_LOGI(AceLogTag::ACE_DRAG, "Leave the current window, windowId is %{public}d,"
655 "PreTargetFrameNode is %{public}s, depth is %{public}d.",
656 container->GetWindowId(), preTargetFrameNode_->GetTag().c_str(), preTargetFrameNode_->GetDepth());
657 FireOnDragEvent(preTargetFrameNode_, pointerEvent, DragEventType::LEAVE, extraInfo_);
658 preTargetFrameNode_ = nullptr;
659 }
660 if (IsNeedDisplayInSubwindow() || isDragWithContextMenu_) {
661 TransDragWindowToDragFwk(Container::CurrentId());
662 }
663 }
664
isDistanceLimited(const Point & point)665 bool DragDropManager::isDistanceLimited(const Point& point)
666 {
667 auto distance = sqrt(pow(point.GetX() - preMovePoint_.GetX(), 2) + pow(point.GetY() - preMovePoint_.GetY(), 2));
668 TAG_LOGD(AceLogTag::ACE_DRAG, "onDragMove, distance: %{public}f", distance);
669 if (distance < MOVE_DISTANCE_LIMIT) {
670 TAG_LOGD(AceLogTag::ACE_DRAG, "onDragMove, distance is less than limit");
671 return true;
672 }
673 return false;
674 }
675
isTimeLimited(const DragPointerEvent & pointerEvent,const Point & point)676 bool DragDropManager::isTimeLimited(const DragPointerEvent& pointerEvent, const Point& point)
677 {
678 uint64_t currentTimeStamp = static_cast<uint64_t>(
679 std::chrono::duration_cast<std::chrono::milliseconds>(pointerEvent.time.time_since_epoch()).count());
680 if (currentTimeStamp > preTimeStamp_ && currentTimeStamp - preTimeStamp_ < MOVE_TIME_LIMIT) {
681 TAG_LOGD(AceLogTag::ACE_DRAG, "onDragMove, time is less than limit");
682 return true;
683 }
684 return false;
685 }
686
ReachMoveLimit(const DragPointerEvent & pointerEvent,const Point & point)687 bool DragDropManager::ReachMoveLimit(const DragPointerEvent& pointerEvent, const Point& point)
688 {
689 if (pointerEvent.sourceTool == SourceTool::MOUSE) {
690 if (isTimeLimited(pointerEvent, point) && isDistanceLimited(point)) {
691 return true;
692 }
693 }
694 return false;
695 }
696
HandleOnDragMove(const DragPointerEvent & pointerEvent,const std::string & extraInfo,const RefPtr<FrameNode> & dragFrameNode)697 void DragDropManager::HandleOnDragMove(const DragPointerEvent& pointerEvent, const std::string& extraInfo,
698 const RefPtr<FrameNode>& dragFrameNode)
699 {
700 CHECK_NULL_VOID(dragFrameNode);
701
702 if (dragFrameNode == preTargetFrameNode_) {
703 FireOnDragEvent(dragFrameNode, pointerEvent, DragEventType::MOVE, extraInfo);
704 return;
705 }
706
707 FireOnDragLeave(preTargetFrameNode_, pointerEvent, extraInfo);
708 PrintDragFrameNode(pointerEvent, dragFrameNode);
709 FireOnDragEvent(dragFrameNode, pointerEvent, DragEventType::ENTER, extraInfo);
710 preTargetFrameNode_ = dragFrameNode;
711 }
712
OnDragMove(const DragPointerEvent & pointerEvent,const std::string & extraInfo,const RefPtr<FrameNode> & node)713 void DragDropManager::OnDragMove(const DragPointerEvent& pointerEvent, const std::string& extraInfo,
714 const RefPtr<FrameNode>& node)
715 {
716 RequireSummaryIfNecessary(pointerEvent);
717 Point point = pointerEvent.GetPoint();
718 auto container = Container::Current();
719 CHECK_NULL_VOID(container);
720 if (container && container->IsScenceBoardWindow()) {
721 if (IsDragged() && IsWindowConsumed()) {
722 SetIsWindowConsumed(false);
723 return;
724 }
725 }
726 if (ReachMoveLimit(pointerEvent, point)) {
727 return;
728 }
729 preMovePoint_ = point;
730 preTimeStamp_ = static_cast<uint64_t>(
731 std::chrono::duration_cast<std::chrono::milliseconds>(pointerEvent.time.time_since_epoch()).count());
732 SetIsWindowConsumed(false);
733 if (isDragFwkShow_) {
734 auto menuWrapper = GetMenuWrapperNodeFromDrag();
735 SubwindowManager::GetInstance()->UpdateHideMenuOffsetNG(OffsetF(static_cast<float>(point.GetX()),
736 static_cast<float>(point.GetY())), 1.0, false, menuWrapper ? menuWrapper->GetId() : -1);
737 }
738 UpdateVelocityTrackerPoint(point, false);
739 UpdateDragListener(point);
740 auto dragFrameNode = FindDragFrameNodeByPosition(
741 static_cast<float>(point.GetX()), static_cast<float>(point.GetY()), node);
742 if (!dragFrameNode) {
743 if (preTargetFrameNode_) {
744 TAG_LOGI(AceLogTag::ACE_DRAG,
745 "Not find drag target node, current windowId is %{public}d,"
746 "pointerEventId is %{public}d. PreTargetFrameNode is %{public}s, depth is %{public}d.",
747 container->GetWindowId(), pointerEvent.pointerEventId, preTargetFrameNode_->GetTag().c_str(),
748 preTargetFrameNode_->GetDepth());
749 FireOnDragEvent(preTargetFrameNode_, pointerEvent, DragEventType::LEAVE, extraInfo);
750 preTargetFrameNode_ = nullptr;
751 }
752
753 if (!isMouseDragged_ || isDragWindowShow_) {
754 UpdateDragStyle(DragCursorStyleCore::MOVE, pointerEvent.pointerEventId);
755 }
756 return;
757 }
758 HandleOnDragMove(pointerEvent, extraInfo, dragFrameNode);
759 }
760
ResetDragDropStatus(const Point & point,const DragDropRet & dragDropRet,int32_t windowId)761 void DragDropManager::ResetDragDropStatus(const Point& point, const DragDropRet& dragDropRet, int32_t windowId)
762 {
763 if (dragDropRet.result != DragRet::DRAG_FAIL || !isMouseDragged_) {
764 InteractionInterface::GetInstance()->SetDragWindowVisible(!dragDropRet.hasCustomAnimation);
765 }
766 InteractionInterface::GetInstance()->StopDrag(dragDropRet);
767 NotifyDragFrameNode(point, DragEventType::DROP, dragDropRet.result);
768 ResetPullId();
769 dragCursorStyleCore_ = DragCursorStyleCore::DEFAULT;
770 }
771
ResetPreTargetFrameNode(int32_t instanceId)772 void DragDropManager::ResetPreTargetFrameNode(int32_t instanceId)
773 {
774 auto container = Container::GetContainer(instanceId);
775 if (container && (container->IsScenceBoardWindow() || container->IsUIExtensionWindow())) {
776 return;
777 }
778 preTargetFrameNode_ = nullptr;
779 }
780
DoDragReset()781 void DragDropManager::DoDragReset()
782 {
783 dragDropState_ = DragDropMgrState::IDLE;
784 preTargetFrameNode_ = nullptr;
785 draggedFrameNode_ = nullptr;
786 menuWrapperNode_ = nullptr;
787 preMovePoint_ = Point(0, 0);
788 hasNotifiedTransformation_ = false;
789 badgeNumber_ = -1;
790 isDragWithContextMenu_ = false;
791 dampingOverflowCount_ = 0;
792 isDragNodeNeedClean_ = false;
793 }
794
ResetDraggingStatus(const TouchEvent & touchPoint)795 void DragDropManager::ResetDraggingStatus(const TouchEvent& touchPoint)
796 {
797 if (IsDraggingPressed(touchPoint.id)) {
798 SetDraggingPressedState(false);
799 }
800 if (!IsItemDragging() && IsDragging() && IsSameDraggingPointer(touchPoint.id)) {
801 OnDragEnd(DragPointerEvent(
802 touchPoint.touchEventId, touchPoint.x, touchPoint.y, touchPoint.screenX, touchPoint.screenY),
803 "");
804 }
805 }
806
HandleOnDragEnd(const DragPointerEvent & pointerEvent,const std::string & extraInfo,const RefPtr<FrameNode> & dragFrameNode)807 void DragDropManager::HandleOnDragEnd(const DragPointerEvent& pointerEvent, const std::string& extraInfo,
808 const RefPtr<FrameNode>& dragFrameNode)
809 {
810 CHECK_NULL_VOID(dragFrameNode);
811 Point point = pointerEvent.GetPoint();
812 auto container = Container::Current();
813 CHECK_NULL_VOID(container);
814 if (!IsDropAllowed(dragFrameNode)) {
815 TAG_LOGI(AceLogTag::ACE_DRAG,
816 "DragDropManager onDragEnd, target data is not allowed to fall into. WindowId is %{public}d, "
817 "pointerEventId is %{public}d.",
818 container->GetWindowId(), pointerEvent.pointerEventId);
819 DragDropBehaviorReporter::GetInstance().UpdateDragStopResult(DragStopResult::APP_REFUSE_DATA);
820 ResetDragDrop(container->GetWindowId(), point);
821 return;
822 }
823 TAG_LOGI(AceLogTag::ACE_DRAG,
824 "Current windowId is %{public}d, pointerEventId is %{public}d. TargetNode is %{public}s.",
825 container->GetWindowId(), pointerEvent.pointerEventId, dragFrameNode->GetTag().c_str());
826 if (IsUIExtensionComponent(dragFrameNode)) {
827 auto pattern = dragFrameNode->GetPattern<Pattern>();
828 pattern->HandleDragEvent(pointerEvent);
829 return;
830 }
831
832 RequestDragSummaryInfoAndPrivilege();
833 std::string udKey;
834 InteractionInterface::GetInstance()->GetUdKey(udKey);
835 auto eventHub = dragFrameNode->GetEventHub<EventHub>();
836 CHECK_NULL_VOID(eventHub);
837 if (!eventHub->GetDisableDataPrefetch()) {
838 if (!CheckRemoteData(dragFrameNode, pointerEvent, udKey)) {
839 auto unifiedData = RequestUDMFDataWithUDKey(udKey);
840 DoDropAction(dragFrameNode, pointerEvent, unifiedData, udKey);
841 }
842 } else {
843 DoDropAction(dragFrameNode, pointerEvent, nullptr, udKey);
844 }
845 }
846
OnDragEnd(const DragPointerEvent & pointerEvent,const std::string & extraInfo,const RefPtr<FrameNode> & node)847 void DragDropManager::OnDragEnd(const DragPointerEvent& pointerEvent, const std::string& extraInfo,
848 const RefPtr<FrameNode>& node)
849 {
850 Point point = pointerEvent.GetPoint();
851 DoDragReset();
852 dragDropPointerEvent_ = pointerEvent;
853 auto container = Container::Current();
854 auto containerId = container->GetInstanceId();
855 DragDropBehaviorReporter::GetInstance().UpdateContainerId(containerId);
856 if (container && container->IsScenceBoardWindow()) {
857 if (IsDragged() && IsWindowConsumed()) {
858 TAG_LOGD(AceLogTag::ACE_DRAG, "DragDropManager is dragged or window consumed. WindowId is %{public}d",
859 container->GetWindowId());
860 return;
861 }
862 }
863 if (isDragCancel_) {
864 DragDropBehaviorReporter::GetInstance().UpdateDragStopResult(DragStopResult::USER_STOP_DRAG);
865 TAG_LOGI(AceLogTag::ACE_DRAG, "DragDropManager is dragCancel, finish drag. WindowId is %{public}d, "
866 "pointerEventId is %{public}d.",
867 container->GetWindowId(), pointerEvent.pointerEventId);
868 DragDropRet dragDropRet { DragRet::DRAG_CANCEL, false, container->GetWindowId(), DragBehavior::UNKNOWN };
869 ResetDragDropStatus(point, dragDropRet, container->GetWindowId());
870 ClearVelocityInfo();
871 return;
872 }
873 UpdateVelocityTrackerPoint(point, true);
874 auto dragFrameNode = FindDragFrameNodeByPosition(
875 static_cast<float>(point.GetX()), static_cast<float>(point.GetY()), node);
876 if (!dragFrameNode) {
877 DragDropBehaviorReporter::GetInstance().UpdateDragStopResult(DragStopResult::APP_DATA_UNSUPPORT);
878 TAG_LOGI(AceLogTag::ACE_DRAG,
879 "DragDropManager onDragEnd, not find drop target, stop drag. WindowId is %{public}d, "
880 "pointerEventId is %{public}d.",
881 container->GetWindowId(), pointerEvent.pointerEventId);
882 ResetDragDrop(container->GetWindowId(), point);
883 return;
884 }
885 HandleOnDragEnd(pointerEvent, extraInfo, dragFrameNode);
886 }
887
IsDropAllowed(const RefPtr<FrameNode> & dragFrameNode)888 bool DragDropManager::IsDropAllowed(const RefPtr<FrameNode>& dragFrameNode)
889 {
890 // application passed in null to indicate refusing all drag data forcedly
891 bool isDisallowDropForcedly = dragFrameNode->GetDisallowDropForcedly();
892 if (isDisallowDropForcedly) {
893 return false;
894 }
895 const auto& dragFrameNodeAllowDrop = dragFrameNode->GetAllowDrop();
896 // if application does not set allow drop or set with empty, treat as all data types is allowed
897 if (dragFrameNodeAllowDrop.empty() || summaryMap_.empty()) {
898 return true;
899 }
900 DragDropBehaviorReporter::GetInstance().UpdateAllowDropType(dragFrameNodeAllowDrop);
901 for (const auto& it : summaryMap_) {
902 // if one matched found, allow drop
903 if (dragFrameNodeAllowDrop.find(it.first) != dragFrameNodeAllowDrop.end()) {
904 return true;
905 }
906 }
907 return false;
908 }
909
RequestDragSummaryInfoAndPrivilege()910 void DragDropManager::RequestDragSummaryInfoAndPrivilege()
911 {
912 RequireSummary();
913 int ret = InteractionInterface::GetInstance()->AddPrivilege();
914 if (ret != 0 && SystemProperties::GetDebugEnabled()) {
915 TAG_LOGD(AceLogTag::ACE_DRAG, "Interaction AddPrivilege in DragEnd with code:%{public}d", ret);
916 }
917 ShadowOffsetData shadowOffsetData { -1, -1, -1, -1 };
918 ret = InteractionInterface::GetInstance()->GetShadowOffset(shadowOffsetData);
919 if (ret == 0) {
920 previewRect_ =
921 Rect(shadowOffsetData.offsetX, shadowOffsetData.offsetY, shadowOffsetData.width, shadowOffsetData.height);
922 } else {
923 TAG_LOGD(AceLogTag::ACE_DRAG, "Interaction GetShadowOffset in DragEnd with code:%{public}d", ret);
924 }
925 }
926
DoDropAction(const RefPtr<FrameNode> & dragFrameNode,const DragPointerEvent & pointerEvent,const RefPtr<UnifiedData> & unifiedData,const std::string & udKey)927 void DragDropManager::DoDropAction(const RefPtr<FrameNode>& dragFrameNode, const DragPointerEvent& pointerEvent,
928 const RefPtr<UnifiedData>& unifiedData, const std::string& udKey)
929 {
930 RefPtr<OHOS::Ace::DragEvent> event = AceType::MakeRefPtr<OHOS::Ace::DragEvent>();
931 if (!udKey.empty()) {
932 event->SetUdKey(udKey);
933 }
934 if (unifiedData == nullptr) {
935 event->SetIsGetDataSuccess(false);
936 } else {
937 DragDropBehaviorReporter::GetInstance().UpdateRecordSize(unifiedData->GetSize());
938 event->SetData(unifiedData);
939 event->SetIsGetDataSuccess(true);
940 }
941 event->SetPressedKeyCodes(pointerEvent.pressedKeyCodes_);
942 OnDragDrop(event, dragFrameNode, pointerEvent);
943 }
944
RequestUDMFDataWithUDKey(const std::string & udKey)945 RefPtr<UnifiedData> DragDropManager::RequestUDMFDataWithUDKey(const std::string& udKey)
946 {
947 if (udKey.empty()) {
948 TAG_LOGI(AceLogTag::ACE_DRAG, "udKey is empty");
949 return nullptr;
950 }
951 RefPtr<UnifiedData> udData = UdmfClient::GetInstance()->CreateUnifiedData();
952 auto ret = UdmfClient::GetInstance()->GetData(udData, udKey);
953 if (ret != 0) {
954 TAG_LOGI(AceLogTag::ACE_DRAG, "Get udmfData failed");
955 return nullptr;
956 }
957 return udData;
958 }
959
TryGetDataBackGround(const RefPtr<FrameNode> & dragFrameNode,const DragPointerEvent & pointerEvent,const std::string & udKey,int32_t count)960 void DragDropManager::TryGetDataBackGround(const RefPtr<FrameNode>& dragFrameNode, const DragPointerEvent& pointerEvent,
961 const std::string& udKey, int32_t count)
962 {
963 auto pipeline = PipelineContext::GetCurrentContext();
964 CHECK_NULL_VOID(pipeline);
965 auto taskScheduler = pipeline->GetTaskExecutor();
966 CHECK_NULL_VOID(taskScheduler);
967 taskScheduler->PostTask(
968 [id = Container::CurrentId(), pipeline, dragFrameNode, pointerEvent, udKey, count,
969 weakManager = WeakClaim(this)]() {
970 ContainerScope scope(id);
971 auto dragDropManager = weakManager.Upgrade();
972 CHECK_NULL_VOID(dragDropManager);
973 auto taskScheduler = pipeline->GetTaskExecutor();
974 CHECK_NULL_VOID(taskScheduler);
975 auto result = dragDropManager->RequestUDMFDataWithUDKey(udKey);
976 if (result != nullptr || count >= MAX_RETRY_TIMES) {
977 taskScheduler->PostTask(
978 [dragFrameNode, pointerEvent, weakManager, result, udKey]() {
979 auto dragDropManager = weakManager.Upgrade();
980 CHECK_NULL_VOID(dragDropManager);
981 dragDropManager->DoDropAction(dragFrameNode, pointerEvent, result, udKey);
982 },
983 TaskExecutor::TaskType::UI, "ArkUIDragDropAction");
984 } else {
985 // first temp get udmfData failed, prepare to retryGetData.
986 taskScheduler->PostDelayedTask(
987 [dragFrameNode, pointerEvent, weakManager, count, udKey]() {
988 auto dragDropManager = weakManager.Upgrade();
989 CHECK_NULL_VOID(dragDropManager);
990 dragDropManager->TryGetDataBackGround(dragFrameNode, pointerEvent, udKey, count + 1);
991 },
992 TaskExecutor::TaskType::UI, MAX_RETRY_DURATION, "ArkUIDragDropRetryGetData");
993 }
994 },
995 TaskExecutor::TaskType::BACKGROUND, "ArkUIDragDropGetDataBackground");
996 }
997
CheckRemoteData(const RefPtr<FrameNode> & dragFrameNode,const DragPointerEvent & pointerEvent,const std::string & udKey)998 bool DragDropManager::CheckRemoteData(
999 const RefPtr<FrameNode>& dragFrameNode, const DragPointerEvent& pointerEvent, const std::string& udKey)
1000 {
1001 if (udKey.empty()) {
1002 DragDropBehaviorReporter::GetInstance().UpdateDragStopResult(DragStopResult::GET_UDKEY_FAIL);
1003 return false;
1004 }
1005 std::string remoteUdKey = udKey;
1006 auto isRemoteData = UdmfClient::GetInstance()->GetRemoteStatus(remoteUdKey);
1007 if (isRemoteData) {
1008 TAG_LOGI(AceLogTag::ACE_DRAG, "Stop drag with motion drag action.");
1009 TryGetDataBackGround(dragFrameNode, pointerEvent, udKey);
1010 DragDropBehaviorReporter::GetInstance().UpdateDragStopResult(DragStopResult::GET_UDKEY_FAIL);
1011 DragDropBehaviorReporter::GetInstance().UpdateIsCrossing(CrossingEnd::IS_CROSSING);
1012 return isRemoteData;
1013 }
1014 DragDropBehaviorReporter::GetInstance().UpdateIsCrossing(CrossingEnd::NOT_CROSSING);
1015 return isRemoteData;
1016 }
1017
OnDragDrop(RefPtr<OHOS::Ace::DragEvent> & event,const RefPtr<FrameNode> & dragFrameNode,const OHOS::Ace::DragPointerEvent & pointerEvent)1018 void DragDropManager::OnDragDrop(RefPtr<OHOS::Ace::DragEvent>& event, const RefPtr<FrameNode>& dragFrameNode,
1019 const OHOS::Ace::DragPointerEvent& pointerEvent)
1020 {
1021 auto point = pointerEvent.GetPoint();
1022 auto eventHub = dragFrameNode->GetEventHub<EventHub>();
1023 CHECK_NULL_VOID(eventHub);
1024 UpdateDragEvent(event, pointerEvent);
1025 auto extraParams = eventHub->GetDragExtraParams(extraInfo_, point, DragEventType::DROP);
1026 eventHub->FireCustomerOnDragFunc(DragFuncType::DRAG_DROP, event, extraParams);
1027 eventHub->HandleInternalOnDrop(event, extraParams);
1028 ClearVelocityInfo();
1029 SetIsDragged(false);
1030 auto pipeline = PipelineContext::GetCurrentContext();
1031 CHECK_NULL_VOID(pipeline);
1032 auto dragResult = event->GetResult();
1033 if (dragResult == DragRet::DRAG_FAIL) {
1034 DragDropBehaviorReporter::GetInstance().UpdateDragStopResult(DragStopResult::APP_RECEIVE_FAIL);
1035 } else if (dragResult == DragRet::DRAG_CANCEL) {
1036 DragDropBehaviorReporter::GetInstance().UpdateDragStopResult(DragStopResult::USER_STOP_DRAG);
1037 }
1038 auto useCustomAnimation = event->IsUseCustomAnimation();
1039 auto dragBehavior = event->GetDragBehavior();
1040 auto container = Container::Current();
1041 CHECK_NULL_VOID(container);
1042 auto windowId = container->GetWindowId();
1043 pipeline->AddAfterRenderTask([dragResult, useCustomAnimation, windowId, dragBehavior,
1044 pointerEventId = pointerEvent.pointerEventId, weak = WeakClaim(this)]() {
1045 TAG_LOGI(AceLogTag::ACE_DRAG,
1046 "Stop drag, start do drop animation. UseCustomAnimation is %{public}d,"
1047 "WindowId is %{public}d, pointerEventId is %{public}d.",
1048 useCustomAnimation, windowId, pointerEventId);
1049 auto manager = weak.Upgrade();
1050 if (manager) {
1051 manager->HideDragPreviewOverlay();
1052 }
1053 InteractionInterface::GetInstance()->SetDragWindowVisible(!useCustomAnimation);
1054 DragDropRet dragDropRet { dragResult, useCustomAnimation, windowId, dragBehavior };
1055 InteractionInterface::GetInstance()->StopDrag(dragDropRet);
1056 });
1057 NotifyDragFrameNode(point, DragEventType::DROP, event->GetResult());
1058 dragFrameNode->MarkDirtyNode();
1059 ResetPullId();
1060 dragCursorStyleCore_ = DragCursorStyleCore::DEFAULT;
1061 pipeline->RequestFrame();
1062 }
1063
RequireSummary()1064 void DragDropManager::RequireSummary()
1065 {
1066 std::map<std::string, int64_t> summary;
1067 int32_t ret = InteractionInterface::GetInstance()->GetDragSummary(summary);
1068 if (ret != 0) {
1069 TAG_LOGI(AceLogTag::ACE_DRAG, "RequireSummary: Interaction GetSummary failed: %{public}d", ret);
1070 } else {
1071 std::string summarys;
1072 for (const auto& [udkey, recordSize] : summary) {
1073 std::string str = udkey + "-" + std::to_string(recordSize) + ";";
1074 summarys += str;
1075 }
1076 TAG_LOGI(AceLogTag::ACE_DRAG, "require summary: %{public}s", summarys.c_str());
1077 DragDropBehaviorReporter::GetInstance().UpdateSummaryType(summarys);
1078 }
1079 std::string extraInfo;
1080 ret = InteractionInterface::GetInstance()->GetDragExtraInfo(extraInfo);
1081 if (ret != 0) {
1082 TAG_LOGI(AceLogTag::ACE_DRAG, "GetExtraInfo: Interaction GetExtraInfo failed: %{public}d", ret);
1083 }
1084 previewRect_ = Rect(-1, -1, -1, -1);
1085 extraInfo_ = extraInfo;
1086 summaryMap_ = summary;
1087 }
1088
ResetRecordSize(uint32_t recordSize)1089 void DragDropManager::ResetRecordSize(uint32_t recordSize)
1090 {
1091 recordSize_ = recordSize;
1092 }
1093
GetRecordSize() const1094 uint32_t DragDropManager::GetRecordSize() const
1095 {
1096 return recordSize_;
1097 }
1098
GetDragWindowRect(const Point & point)1099 Rect DragDropManager::GetDragWindowRect(const Point& point)
1100 {
1101 if (!previewRect_.IsValid()) {
1102 ShadowOffsetData shadowOffsetData { -1, -1, -1, -1 };
1103 int ret = InteractionInterface::GetInstance()->GetShadowOffset(shadowOffsetData);
1104 if (ret == 0) {
1105 previewRect_ = Rect(
1106 shadowOffsetData.offsetX,
1107 shadowOffsetData.offsetY,
1108 shadowOffsetData.width,
1109 shadowOffsetData.height);
1110 }
1111 }
1112 return previewRect_ + Offset(point.GetX(), point.GetY());
1113 }
1114
ClearSummary()1115 void DragDropManager::ClearSummary()
1116 {
1117 previewRect_ = Rect(-1, -1, -1, -1);
1118 ResetPullId();
1119 ResetRecordSize();
1120 }
1121
OnTextDragEnd(float globalX,float globalY,const std::string & extraInfo)1122 void DragDropManager::OnTextDragEnd(float globalX, float globalY, const std::string& extraInfo)
1123 {
1124 dragDropState_ = DragDropMgrState::IDLE;
1125 auto dragFrameNode = FindDragFrameNodeByPosition(globalX, globalY);
1126 if (dragFrameNode) {
1127 auto textFieldPattern = dragFrameNode->GetPattern<TextFieldPattern>();
1128 if (textFieldPattern) {
1129 textFieldPattern->InsertValue(extraInfo);
1130 }
1131 }
1132 SetIsDragged(false);
1133 currentId_ = -1;
1134 }
1135
onDragCancel()1136 void DragDropManager::onDragCancel()
1137 {
1138 preTargetFrameNode_ = nullptr;
1139 draggedFrameNode_ = nullptr;
1140 }
1141
FireOnDragEventWithDragType(const RefPtr<EventHub> & eventHub,DragEventType type,RefPtr<OHOS::Ace::DragEvent> & event,const std::string & extraParams)1142 void DragDropManager::FireOnDragEventWithDragType(const RefPtr<EventHub>& eventHub, DragEventType type,
1143 RefPtr<OHOS::Ace::DragEvent>& event, const std::string& extraParams)
1144 {
1145 switch (type) {
1146 case DragEventType::ENTER: {
1147 eventHub->FireCustomerOnDragFunc(DragFuncType::DRAG_ENTER, event, extraParams);
1148 eventHub->FireOnDragEnter(event, extraParams);
1149 break;
1150 }
1151 case DragEventType::MOVE: {
1152 eventHub->FireCustomerOnDragFunc(DragFuncType::DRAG_MOVE, event, extraParams);
1153 eventHub->FireOnDragMove(event, extraParams);
1154 break;
1155 }
1156 case DragEventType::LEAVE: {
1157 eventHub->FireCustomerOnDragFunc(DragFuncType::DRAG_LEAVE, event, extraParams);
1158 eventHub->FireOnDragLeave(event, extraParams);
1159 break;
1160 }
1161 case DragEventType::DROP: {
1162 eventHub->FireCustomerOnDragFunc(DragFuncType::DRAG_DROP, event, extraParams);
1163 eventHub->HandleInternalOnDrop(event, extraParams);
1164 break;
1165 }
1166 default:
1167 break;
1168 }
1169 }
1170
FireOnDragEvent(const RefPtr<FrameNode> & frameNode,const DragPointerEvent & pointerEvent,DragEventType type,const std::string & extraInfo)1171 void DragDropManager::FireOnDragEvent(
1172 const RefPtr<FrameNode>& frameNode, const DragPointerEvent& pointerEvent,
1173 DragEventType type, const std::string& extraInfo)
1174 {
1175 if (IsUIExtensionComponent(frameNode)) {
1176 auto dragEvent = pointerEvent;
1177 if (type == DragEventType::ENTER) {
1178 dragEvent.action = PointerAction::PULL_IN_WINDOW;
1179 } else if (type == DragEventType::LEAVE) {
1180 dragEvent.action = PointerAction::PULL_OUT_WINDOW;
1181 }
1182 auto pattern = frameNode->GetPattern<Pattern>();
1183 CHECK_NULL_VOID(pattern);
1184 pattern->HandleDragEvent(dragEvent);
1185 return;
1186 }
1187 auto eventHub = frameNode->GetEventHub<EventHub>();
1188 CHECK_NULL_VOID(eventHub);
1189 auto pipeline = PipelineContext::GetCurrentContext();
1190 CHECK_NULL_VOID(pipeline);
1191 if (!eventHub->HasOnDrop() && !eventHub->HasOnItemDrop() && !eventHub->HasCustomerOnDrop()) {
1192 return;
1193 }
1194 auto point = pointerEvent.GetPoint();
1195 auto extraParams = eventHub->GetDragExtraParams(extraInfo_.empty() ? extraInfo : extraInfo_, point, type);
1196 RefPtr<OHOS::Ace::DragEvent> event = AceType::MakeRefPtr<OHOS::Ace::DragEvent>();
1197 event->SetX((double)point.GetX());
1198 event->SetY((double)point.GetY());
1199 event->SetScreenX((double)point.GetScreenX());
1200 event->SetScreenY((double)point.GetScreenY());
1201 event->SetDisplayX((double)pointerEvent.GetDisplayX());
1202 event->SetDisplayY((double)pointerEvent.GetDisplayY());
1203 event->SetVelocity(velocityTracker_.GetVelocity());
1204 event->SetSummary(summaryMap_);
1205 event->SetPreviewRect(GetDragWindowRect(point));
1206 event->SetPressedKeyCodes(pointerEvent.pressedKeyCodes_);
1207
1208 FireOnEditableTextComponent(frameNode, type);
1209 FireOnDragEventWithDragType(eventHub, type, event, extraParams);
1210
1211 if (isMouseDragged_ && !isDragWindowShow_) {
1212 return;
1213 }
1214 if (event->GetResult() == DragRet::ENABLE_DROP) {
1215 if (event->GetDragBehavior() == DragBehavior::MOVE) {
1216 UpdateDragStyle(DragCursorStyleCore::MOVE, pointerEvent.pointerEventId);
1217 } else {
1218 UpdateDragStyle(DragCursorStyleCore::COPY, pointerEvent.pointerEventId);
1219 }
1220 } else if (event->GetResult() == DragRet::DISABLE_DROP) {
1221 // simplified specifications for drag cursor style, no longer showing forbidden drag cursor
1222 UpdateDragStyle(DragCursorStyleCore::MOVE, pointerEvent.pointerEventId);
1223 } else {
1224 UpdateDragAllowDrop(frameNode, event->GetDragBehavior(), pointerEvent.pointerEventId, event->IsCapi());
1225 }
1226 }
1227
OnItemDragStart(float globalX,float globalY,const RefPtr<FrameNode> & frameNode)1228 void DragDropManager::OnItemDragStart(float globalX, float globalY, const RefPtr<FrameNode>& frameNode)
1229 {
1230 dragDropState_ = DragDropMgrState::DRAGGING;
1231 preGridTargetFrameNode_ = frameNode;
1232 draggedGridFrameNode_ = frameNode;
1233 }
1234
OnItemDragMove(float globalX,float globalY,int32_t draggedIndex,DragType dragType)1235 void DragDropManager::OnItemDragMove(float globalX, float globalY, int32_t draggedIndex, DragType dragType)
1236 {
1237 auto container = Container::Current();
1238 CHECK_NULL_VOID(container);
1239
1240 UpdateItemDragPosition(globalX, globalY);
1241
1242 OHOS::Ace::ItemDragInfo itemDragInfo;
1243 itemDragInfo.SetX(globalX);
1244 itemDragInfo.SetY(globalY);
1245
1246 // use -1 for grid item not in eventGrid
1247 auto getDraggedIndex = [draggedGrid = draggedGridFrameNode_, draggedIndex, dragType](
1248 const RefPtr<FrameNode>& eventGrid) {
1249 return (dragType == DragType::GRID) ? (eventGrid == draggedGrid ? draggedIndex : -1) : draggedIndex;
1250 };
1251
1252 auto dragFrameNode = FindDragFrameNodeByPosition(globalX, globalY);
1253 if (!dragFrameNode) {
1254 if (preGridTargetFrameNode_) {
1255 TAG_LOGI(AceLogTag::ACE_DRAG, "Not find drag target node, current windowId is %{public}d,"
1256 "PreGridTargetFrameNode is %{public}s, depth is %{public}d.",
1257 container->GetWindowId(), preGridTargetFrameNode_->GetTag().c_str(),
1258 preGridTargetFrameNode_->GetDepth());
1259 FireOnItemDragEvent(preGridTargetFrameNode_, dragType, itemDragInfo, DragEventType::LEAVE,
1260 getDraggedIndex(preGridTargetFrameNode_));
1261 preGridTargetFrameNode_ = nullptr;
1262 }
1263 return;
1264 }
1265
1266 if (dragFrameNode == preGridTargetFrameNode_) {
1267 int32_t insertIndex = GetItemIndex(dragFrameNode, dragType, globalX, globalY);
1268 FireOnItemDragEvent(
1269 dragFrameNode, dragType, itemDragInfo, DragEventType::MOVE, getDraggedIndex(dragFrameNode), insertIndex);
1270 return;
1271 }
1272
1273 if (preGridTargetFrameNode_) {
1274 FireOnItemDragEvent(preGridTargetFrameNode_, dragType, itemDragInfo, DragEventType::LEAVE,
1275 getDraggedIndex(preGridTargetFrameNode_));
1276 }
1277
1278 PrintGridDragFrameNode(globalX, globalY, dragFrameNode);
1279 FireOnItemDragEvent(dragFrameNode, dragType, itemDragInfo, DragEventType::ENTER, getDraggedIndex(dragFrameNode));
1280 preGridTargetFrameNode_ = dragFrameNode;
1281 }
1282
GetWindowScale() const1283 float DragDropManager::GetWindowScale() const
1284 {
1285 float scale = 1.0f;
1286 auto container = Container::Current();
1287 CHECK_NULL_RETURN(container, scale);
1288 scale = container->GetWindowScale();
1289 return scale;
1290 }
1291
OnItemDragEnd(float globalX,float globalY,int32_t draggedIndex,DragType dragType)1292 void DragDropManager::OnItemDragEnd(float globalX, float globalY, int32_t draggedIndex, DragType dragType)
1293 {
1294 dragDropState_ = DragDropMgrState::IDLE;
1295 auto windowScale = isDragWindowSubWindow_ ? 1.0f : GetWindowScale();
1296 auto windowX = globalX * windowScale;
1297 auto windowY = globalY * windowScale;
1298
1299 OHOS::Ace::ItemDragInfo itemDragInfo;
1300 itemDragInfo.SetX(windowX);
1301 itemDragInfo.SetY(windowY);
1302
1303 auto dragFrameNode = FindDragFrameNodeByPosition(globalX, globalY);
1304 if (!dragFrameNode) {
1305 // drag on one grid and drop on other area
1306 if (draggedGridFrameNode_) {
1307 if (dragType == DragType::GRID) {
1308 auto eventHub = draggedGridFrameNode_->GetEventHub<GridEventHub>();
1309 CHECK_NULL_VOID(eventHub);
1310 eventHub->FireOnItemDrop(itemDragInfo, draggedIndex, -1, false);
1311 } else {
1312 auto eventHub = draggedGridFrameNode_->GetEventHub<ListEventHub>();
1313 CHECK_NULL_VOID(eventHub);
1314 eventHub->FireOnItemDrop(itemDragInfo, draggedIndex, -1, false);
1315 }
1316 }
1317 } else {
1318 int32_t insertIndex = GetItemIndex(dragFrameNode, dragType, globalX, globalY);
1319 // drag and drop on the same grid
1320 if (dragFrameNode == draggedGridFrameNode_) {
1321 FireOnItemDropEvent(dragFrameNode, dragType, itemDragInfo, draggedIndex, insertIndex, true);
1322 } else {
1323 // drag and drop on different grid
1324 bool isSuccess = FireOnItemDropEvent(dragFrameNode, dragType, itemDragInfo, -1, insertIndex, true);
1325 if (draggedGridFrameNode_) {
1326 FireOnItemDropEvent(draggedGridFrameNode_, dragType, itemDragInfo, draggedIndex, -1, isSuccess);
1327 }
1328 }
1329 }
1330
1331 preGridTargetFrameNode_ = nullptr;
1332 draggedGridFrameNode_ = nullptr;
1333 }
1334
onItemDragCancel()1335 void DragDropManager::onItemDragCancel()
1336 {
1337 dragDropState_ = DragDropMgrState::IDLE;
1338 preGridTargetFrameNode_ = nullptr;
1339 draggedGridFrameNode_ = nullptr;
1340 }
1341
FireOnItemDragEvent(const RefPtr<FrameNode> & frameNode,DragType dragType,const OHOS::Ace::ItemDragInfo & itemDragInfo,DragEventType type,int32_t draggedIndex,int32_t insertIndex)1342 void DragDropManager::FireOnItemDragEvent(const RefPtr<FrameNode>& frameNode, DragType dragType,
1343 const OHOS::Ace::ItemDragInfo& itemDragInfo, DragEventType type, int32_t draggedIndex, int32_t insertIndex)
1344 {
1345 if (dragType == DragType::GRID) {
1346 auto eventHub = frameNode->GetEventHub<GridEventHub>();
1347 CHECK_NULL_VOID(eventHub);
1348 switch (type) {
1349 case DragEventType::ENTER:
1350 eventHub->FireOnItemDragEnter(itemDragInfo);
1351 break;
1352 case DragEventType::MOVE:
1353 eventHub->FireOnItemDragMove(itemDragInfo, draggedIndex, insertIndex);
1354 break;
1355 case DragEventType::LEAVE:
1356 eventHub->FireOnItemDragLeave(itemDragInfo, draggedIndex);
1357 break;
1358 default:
1359 break;
1360 }
1361 } else if (dragType == DragType::LIST) {
1362 auto eventHub = frameNode->GetEventHub<ListEventHub>();
1363 CHECK_NULL_VOID(eventHub);
1364 switch (type) {
1365 case DragEventType::ENTER:
1366 eventHub->FireOnItemDragEnter(itemDragInfo);
1367 break;
1368 case DragEventType::MOVE:
1369 eventHub->FireOnItemDragMove(itemDragInfo, draggedIndex, insertIndex);
1370 break;
1371 case DragEventType::LEAVE:
1372 eventHub->FireOnItemDragLeave(itemDragInfo, draggedIndex);
1373 break;
1374 default:
1375 break;
1376 }
1377 }
1378 }
1379
FireOnItemDropEvent(const RefPtr<FrameNode> & frameNode,DragType dragType,const OHOS::Ace::ItemDragInfo & itemDragInfo,int32_t draggedIndex,int32_t insertIndex,bool isSuccess)1380 bool DragDropManager::FireOnItemDropEvent(const RefPtr<FrameNode>& frameNode, DragType dragType,
1381 const OHOS::Ace::ItemDragInfo& itemDragInfo, int32_t draggedIndex, int32_t insertIndex, bool isSuccess)
1382 {
1383 if (dragType == DragType::GRID) {
1384 auto eventHub = frameNode->GetEventHub<GridEventHub>();
1385 CHECK_NULL_RETURN(eventHub, false);
1386 return eventHub->FireOnItemDrop(itemDragInfo, draggedIndex, insertIndex, isSuccess);
1387 } else if (dragType == DragType::LIST) {
1388 auto eventHub = frameNode->GetEventHub<ListEventHub>();
1389 CHECK_NULL_RETURN(eventHub, false);
1390 return eventHub->FireOnItemDrop(itemDragInfo, draggedIndex, insertIndex, isSuccess);
1391 }
1392 return false;
1393 }
1394
GetItemIndex(const RefPtr<FrameNode> & frameNode,DragType dragType,float globalX,float globalY)1395 int32_t DragDropManager::GetItemIndex(
1396 const RefPtr<FrameNode>& frameNode, DragType dragType, float globalX, float globalY)
1397 {
1398 CHECK_NULL_RETURN(frameNode, -1);
1399 if (dragType == DragType::GRID) {
1400 auto eventHub = frameNode->GetEventHub<GridEventHub>();
1401 CHECK_NULL_RETURN(eventHub, -1);
1402 if (frameNode != draggedGridFrameNode_) {
1403 return eventHub->GetInsertPosition(globalX, globalY);
1404 }
1405 auto itemFrameNode = frameNode->FindChildByPositionWithoutChildTransform(globalX, globalY);
1406 if (!itemFrameNode) {
1407 if (eventHub->CheckPostionInGrid(globalX, globalY)) {
1408 return eventHub->GetFrameNodeChildSize();
1409 }
1410 } else {
1411 return eventHub->GetGridItemIndex(itemFrameNode);
1412 }
1413 } else if (dragType == DragType::LIST) {
1414 auto eventHub = frameNode->GetEventHub<ListEventHub>();
1415 CHECK_NULL_RETURN(eventHub, -1);
1416 return eventHub->GetListItemIndexByPosition(globalX, globalY);
1417 }
1418 return -1;
1419 }
1420
AddDataToClipboard(const std::string & extraInfo)1421 void DragDropManager::AddDataToClipboard(const std::string& extraInfo)
1422 {
1423 auto pipeline = PipelineContext::GetCurrentContext();
1424 CHECK_NULL_VOID(pipeline);
1425 if (!extraInfo.empty()) {
1426 if (!newData_) {
1427 newData_ = JsonUtil::Create(true);
1428 newData_->Put("customDragInfo", extraInfo.c_str());
1429 } else {
1430 newData_->Replace("customDragInfo", extraInfo.c_str());
1431 }
1432 } else {
1433 return;
1434 }
1435 if (!clipboard_) {
1436 clipboard_ = ClipboardProxy::GetInstance()->GetClipboard(pipeline->GetTaskExecutor());
1437 }
1438 if (!addDataCallback_) {
1439 auto callback = [weakManager = WeakClaim(this)](const std::string& data) {
1440 auto dragDropManager = weakManager.Upgrade();
1441 auto addData = dragDropManager->newData_->ToString();
1442 CHECK_NULL_VOID(dragDropManager);
1443 auto clipboardAllData = JsonUtil::Create(true);
1444 clipboardAllData->Put("preData", data.c_str());
1445 clipboardAllData->Put("newData", addData.c_str());
1446 dragDropManager->clipboard_->SetData(clipboardAllData->ToString(), CopyOptions::Local, true);
1447 };
1448 addDataCallback_ = callback;
1449 }
1450 if (clipboard_) {
1451 clipboard_->GetData(addDataCallback_, true);
1452 }
1453 }
1454
GetExtraInfoFromClipboard(std::string & extraInfo)1455 void DragDropManager::GetExtraInfoFromClipboard(std::string& extraInfo)
1456 {
1457 auto pipeline = PipelineContext::GetCurrentContext();
1458 CHECK_NULL_VOID(pipeline);
1459
1460 if (!clipboard_) {
1461 clipboard_ = ClipboardProxy::GetInstance()->GetClipboard(pipeline->GetTaskExecutor());
1462 }
1463
1464 if (!getDataCallback_) {
1465 auto callback = [weak = WeakClaim(this)](const std::string& data) {
1466 auto manager = weak.Upgrade();
1467 CHECK_NULL_VOID(manager);
1468 auto json = JsonUtil::ParseJsonString(data);
1469 auto newData = JsonUtil::ParseJsonString(json->GetString("newData"));
1470 manager->extraInfo_ = newData->GetString("customDragInfo");
1471 };
1472 getDataCallback_ = callback;
1473 }
1474
1475 if (getDataCallback_ && clipboard_) {
1476 clipboard_->GetData(getDataCallback_, true);
1477 }
1478
1479 extraInfo = extraInfo_;
1480 }
1481
RestoreClipboardData()1482 void DragDropManager::RestoreClipboardData()
1483 {
1484 auto pipeline = PipelineContext::GetCurrentContext();
1485 CHECK_NULL_VOID(pipeline);
1486
1487 if (!clipboard_) {
1488 clipboard_ = ClipboardProxy::GetInstance()->GetClipboard(pipeline->GetTaskExecutor());
1489 }
1490
1491 if (!deleteDataCallback_) {
1492 auto callback = [weakManager = WeakClaim(this)](const std::string& data) {
1493 auto dragDropManager = weakManager.Upgrade();
1494 CHECK_NULL_VOID(dragDropManager);
1495 auto json = JsonUtil::ParseJsonString(data);
1496 if (json->Contains("preData")) {
1497 dragDropManager->clipboard_->SetData(json->GetString("preData"));
1498 }
1499 };
1500 deleteDataCallback_ = callback;
1501 }
1502 if (clipboard_) {
1503 clipboard_->GetData(deleteDataCallback_, true);
1504 }
1505 }
1506
DestroyDragWindow()1507 void DragDropManager::DestroyDragWindow()
1508 {
1509 ResetRecordSize();
1510 if (itemDragOverlayNode_) {
1511 RemoveItemDrag();
1512 itemDragOverlayNode_ = nullptr;
1513 }
1514 SetIsDragged(false);
1515 SetIsDragWindowShow(false);
1516 previewRect_ = Rect(-1, -1, -1, -1);
1517 isMouseDragged_ = false;
1518 currentId_ = -1;
1519 }
1520
CancelItemDrag()1521 void DragDropManager::CancelItemDrag()
1522 {
1523 if (draggedGridFrameNode_) {
1524 auto listEventHub = draggedGridFrameNode_->GetEventHub<ListEventHub>();
1525 if (listEventHub) {
1526 listEventHub->HandleOnItemDragCancel();
1527 return;
1528 }
1529 auto gridEventHub = draggedGridFrameNode_->GetEventHub<GridEventHub>();
1530 if (gridEventHub) {
1531 gridEventHub->HandleOnItemDragCancel();
1532 return;
1533 }
1534 }
1535 }
1536
CreateFrameworkDragDropProxy()1537 RefPtr<DragDropProxy> DragDropManager::CreateFrameworkDragDropProxy()
1538 {
1539 SetIsDragged(true);
1540 isDragCancel_ = false;
1541 currentId_ = ++g_proxyId;
1542 return MakeRefPtr<DragDropProxy>(currentId_);
1543 }
1544
UpdateNotifyDragEvent(RefPtr<NotifyDragEvent> & notifyEvent,const Point & point,const DragEventType dragEventType)1545 void DragDropManager::UpdateNotifyDragEvent(
1546 RefPtr<NotifyDragEvent>& notifyEvent, const Point& point, const DragEventType dragEventType)
1547 {
1548 notifyEvent->SetX((double)point.GetX());
1549 notifyEvent->SetY((double)point.GetY());
1550 notifyEvent->SetScreenX((double)point.GetScreenX());
1551 notifyEvent->SetScreenY((double)point.GetScreenY());
1552 if (dragEventType != DragEventType::START) {
1553 if (dragEventType != DragEventType::DROP) {
1554 notifyEvent->SetVelocity(velocityTracker_.GetVelocity());
1555 }
1556 notifyEvent->SetSummary(summaryMap_);
1557 notifyEvent->SetPreviewRect(GetDragWindowRect(point));
1558 }
1559 }
1560
UpdateDragEvent(RefPtr<OHOS::Ace::DragEvent> & event,const OHOS::Ace::DragPointerEvent & pointerEvent)1561 void DragDropManager::UpdateDragEvent(
1562 RefPtr<OHOS::Ace::DragEvent>& event, const OHOS::Ace::DragPointerEvent& pointerEvent)
1563 {
1564 auto point = pointerEvent.GetPoint();
1565 event->SetX(point.GetX());
1566 event->SetY(point.GetY());
1567 event->SetScreenX(point.GetScreenX());
1568 event->SetScreenY(point.GetScreenY());
1569 event->SetDisplayX((double)pointerEvent.GetDisplayX());
1570 event->SetDisplayY((double)pointerEvent.GetDisplayY());
1571 event->SetVelocity(velocityTracker_.GetVelocity());
1572 event->SetSummary(summaryMap_);
1573 event->SetPreviewRect(GetDragWindowRect(point));
1574 }
1575
GetExtraInfo()1576 std::string DragDropManager::GetExtraInfo()
1577 {
1578 return extraInfo_;
1579 }
1580
SetExtraInfo(const std::string & extraInfo)1581 void DragDropManager::SetExtraInfo(const std::string& extraInfo)
1582 {
1583 extraInfo_ = extraInfo;
1584 }
1585
ClearExtraInfo()1586 void DragDropManager::ClearExtraInfo()
1587 {
1588 extraInfo_.clear();
1589 }
1590
IsMSDPDragging() const1591 bool DragDropManager::IsMSDPDragging() const
1592 {
1593 DragState dragState;
1594 InteractionInterface::GetInstance()->GetDragState(dragState);
1595 return dragState == DragState::START;
1596 }
1597
ClearVelocityInfo()1598 void DragDropManager::ClearVelocityInfo()
1599 {
1600 velocityTracker_.Reset();
1601 }
1602
UpdateVelocityTrackerPoint(const Point & point,bool isEnd)1603 void DragDropManager::UpdateVelocityTrackerPoint(const Point& point, bool isEnd)
1604 {
1605 std::chrono::microseconds microseconds(GetMicroTickCount());
1606 TimeStamp curTime(microseconds);
1607 velocityTracker_.UpdateTrackerPoint(point.GetX(), point.GetY(), curTime, isEnd);
1608 }
1609
NotifyEnterTextEditorArea()1610 void DragDropManager::NotifyEnterTextEditorArea()
1611 {
1612 auto ret = InteractionInterface::GetInstance()->EnterTextEditorArea(true);
1613 if (ret != 0) {
1614 TAG_LOGW(AceLogTag::ACE_DRAG, "Fail to notify entering text editor erea.");
1615 return;
1616 }
1617
1618 hasNotifiedTransformation_ = true;
1619 }
1620
FireOnEditableTextComponent(const RefPtr<FrameNode> & frameNode,DragEventType type)1621 void DragDropManager::FireOnEditableTextComponent(const RefPtr<FrameNode>& frameNode,
1622 DragEventType type)
1623 {
1624 CHECK_NULL_VOID(frameNode);
1625 auto frameTag = frameNode->GetTag();
1626 auto eventHub = frameNode->GetEventHub<EventHub>();
1627 if (!IsEditableTextComponent(frameTag) || !(eventHub && eventHub->IsEnabled()) || !isDragFwkShow_) {
1628 return;
1629 }
1630
1631 // When moving in an editable text component whithout animation, and has not notified msdp yet, notify msdp.
1632 if (type == DragEventType::MOVE && IsEditableTextComponent(frameTag) && isDragFwkShow_ &&
1633 !hasNotifiedTransformation_) {
1634 NotifyEnterTextEditorArea();
1635 return;
1636 }
1637 if (type != DragEventType::ENTER && type != DragEventType::LEAVE) {
1638 TAG_LOGD(AceLogTag::ACE_DRAG, "It is an invalid drag type %{public}d", type);
1639 return;
1640 }
1641
1642 if (type == DragEventType::LEAVE) {
1643 TAG_LOGI(AceLogTag::ACE_DRAG, "The current control has been dragged away.");
1644 hasNotifiedTransformation_ = false;
1645 return;
1646 }
1647
1648 if (hasNotifiedTransformation_) {
1649 TAG_LOGI(AceLogTag::ACE_DRAG, "Coordinates have been transformed.");
1650 return;
1651 }
1652
1653 NotifyEnterTextEditorArea();
1654 }
1655
GetDragPreviewInfo(const RefPtr<OverlayManager> & overlayManager,DragPreviewInfo & dragPreviewInfo,const RefPtr<GestureEventHub> & gestureHub)1656 bool DragDropManager::GetDragPreviewInfo(const RefPtr<OverlayManager>& overlayManager,
1657 DragPreviewInfo& dragPreviewInfo, const RefPtr<GestureEventHub>& gestureHub)
1658 {
1659 if (!overlayManager->GetHasDragPixelMap()) {
1660 return false;
1661 }
1662 auto imageNode = overlayManager->GetDragPixelMapContentNode();
1663 CHECK_NULL_RETURN(imageNode, false);
1664 auto badgeNode = overlayManager->GetDragPixelMapBadgeNode();
1665 if (badgeNode) {
1666 dragPreviewInfo.textNode = badgeNode;
1667 }
1668 CHECK_NULL_RETURN(gestureHub, false);
1669 auto frameNode = gestureHub->GetFrameNode();
1670 double maxWidth = DragDropManager::GetMaxWidthBaseOnGridSystem(frameNode->GetContextRefPtr());
1671 auto width = imageNode->GetGeometryNode()->GetFrameRect().Width();
1672 auto previewOption = imageNode->GetDragPreviewOption();
1673 if (imageNode->GetTag() != V2::WEB_ETS_TAG && width != 0 && width > maxWidth && previewOption.isScaleEnabled) {
1674 dragPreviewInfo.scale = maxWidth / width;
1675 } else {
1676 dragPreviewInfo.scale = 1.0f;
1677 }
1678
1679 if (!isMouseDragged_ && dragPreviewInfo.scale == 1.0f) {
1680 dragPreviewInfo.scale = TOUCH_DRAG_PIXELMAP_SCALE;
1681 }
1682 // set menu preview scale only for no scale menu preview.
1683 if (isDragWithContextMenu_ && (!previewOption.isScaleEnabled || width < maxWidth)) {
1684 auto imageGestureEventHub = imageNode->GetOrCreateGestureEventHub();
1685 if (imageGestureEventHub) {
1686 auto menuPreviewScale = imageGestureEventHub->GetMenuPreviewScale();
1687 dragPreviewInfo.scale =
1688 GreatNotEqual(menuPreviewScale, 0.0f) ? menuPreviewScale : TOUCH_DRAG_PIXELMAP_SCALE;
1689 }
1690 }
1691 dragPreviewInfo.height = imageNode->GetGeometryNode()->GetFrameRect().Height();
1692 dragPreviewInfo.width = static_cast<double>(width);
1693 dragPreviewInfo.maxWidth = maxWidth;
1694 dragPreviewInfo.imageNode = imageNode;
1695 dragPreviewInfo.originOffset = imageNode->GetPositionToWindowWithTransform();
1696 dragPreviewInfo.originScale = imageNode->GetTransformScale();
1697 return true;
1698 }
1699
IsNeedDoDragMoveAnimate(const DragPointerEvent & pointerEvent)1700 bool DragDropManager::IsNeedDoDragMoveAnimate(const DragPointerEvent& pointerEvent)
1701 {
1702 if (!(IsNeedDisplayInSubwindow() || isDragWithContextMenu_) || isDragFwkShow_) {
1703 return false;
1704 }
1705 auto x = pointerEvent.GetPoint().GetX();
1706 auto y = pointerEvent.GetPoint().GetY();
1707 curPointerOffset_ = { x, y };
1708 return true;
1709 }
1710
IsNeedScaleDragPreview()1711 bool DragDropManager::IsNeedScaleDragPreview()
1712 {
1713 return info_.scale > 0 && info_.scale < 1.0f;
1714 }
1715
GetTouchOffsetRelativeToSubwindow(int32_t x,int32_t y)1716 OffsetF GetTouchOffsetRelativeToSubwindow(int32_t x, int32_t y)
1717 {
1718 auto touchOffset = OffsetF(x, y);
1719 auto pipeline = PipelineContext::GetCurrentContext();
1720 if (pipeline) {
1721 auto window = pipeline->GetWindow();
1722 if (window) {
1723 auto windowOffset = window->GetCurrentWindowRect().GetOffset();
1724 touchOffset.SetX(touchOffset.GetX() + windowOffset.GetX());
1725 touchOffset.SetY(touchOffset.GetY() + windowOffset.GetY());
1726 }
1727 }
1728 auto containerId = Container::CurrentId();
1729 auto subwindow = SubwindowManager::GetInstance()->GetSubwindow(
1730 containerId >= MIN_SUBCONTAINER_ID ? SubwindowManager::GetInstance()->GetParentContainerId(containerId)
1731 : containerId);
1732 if (subwindow) {
1733 auto subwindowOffset = subwindow->GetRect().GetOffset();
1734 touchOffset.SetX(touchOffset.GetX() - subwindowOffset.GetX());
1735 touchOffset.SetY(touchOffset.GetY() - subwindowOffset.GetY());
1736 }
1737 return touchOffset;
1738 }
1739
CalcDragPreviewDistanceWithPoint(const OHOS::Ace::Dimension & preserverHeight,int32_t x,int32_t y,const DragPreviewInfo & info)1740 double DragDropManager::CalcDragPreviewDistanceWithPoint(
1741 const OHOS::Ace::Dimension& preserverHeight, int32_t x, int32_t y, const DragPreviewInfo& info)
1742 {
1743 CHECK_NULL_RETURN(info.imageNode, 0.0);
1744 auto nodeOffset = info.imageNode->GetTransformRelativeOffset();
1745 auto renderContext = info.imageNode->GetRenderContext();
1746 CHECK_NULL_RETURN(renderContext, 0.0);
1747 nodeOffset -= pixelMapOffset_;
1748 auto touchOffset = GetTouchOffsetRelativeToSubwindow(x, y);
1749 // calculate distance, so need to pow 2.
1750 return sqrt(pow(nodeOffset.GetX() - touchOffset.GetX(), 2) + pow(nodeOffset.GetY() - touchOffset.GetY(), 2));
1751 }
1752
CalcDragMoveOffset(const OHOS::Ace::Dimension & preserverHeight,int32_t x,int32_t y,const DragPreviewInfo & info)1753 Offset DragDropManager::CalcDragMoveOffset(
1754 const OHOS::Ace::Dimension& preserverHeight, int32_t x, int32_t y, const DragPreviewInfo& info)
1755 {
1756 auto originPoint = info.originOffset;
1757 originPoint.SetX(originPoint.GetX() - pixelMapOffset_.GetX() +
1758 (info.originScale.x - info.scale) * info.width / 2.0f);
1759 originPoint.SetY(originPoint.GetY() - pixelMapOffset_.GetY() +
1760 (info.originScale.y - info.scale) * info.height / 2.0f);
1761 auto touchOffset = GetTouchOffsetRelativeToSubwindow(x, y);
1762 Offset newOffset { touchOffset.GetX() - originPoint.GetX(), touchOffset.GetY() - originPoint.GetY() };
1763 return newOffset;
1764 }
1765
UpdateDragMovePositionFinished(bool needDoDragMoveAnimate,bool isMenuShow,const Offset & newOffset,int32_t containerId)1766 bool DragDropManager::UpdateDragMovePositionFinished(
1767 bool needDoDragMoveAnimate, bool isMenuShow, const Offset& newOffset, int32_t containerId)
1768 {
1769 if (!isDragWithContextMenu_) {
1770 return false;
1771 }
1772
1773 CHECK_NULL_RETURN(info_.imageNode, false);
1774 auto renderContext = info_.imageNode->GetRenderContext();
1775 CHECK_NULL_RETURN(renderContext, false);
1776 SubwindowManager::GetInstance()->ContextMenuSwitchDragPreviewAnimation(info_.imageNode,
1777 OffsetF(newOffset.GetX(), newOffset.GetY()));
1778 if (!needDoDragMoveAnimate) {
1779 renderContext->UpdateTransformTranslate({ newOffset.GetX(), newOffset.GetY(), 0.0f });
1780 if (!isMenuShow) {
1781 TransDragWindowToDragFwk(containerId);
1782 }
1783 return true;
1784 }
1785 return false;
1786 }
1787
GetCurrentDistance(float x,float y)1788 float DragDropManager::GetCurrentDistance(float x, float y)
1789 {
1790 auto distance = sqrt(pow(curPointerOffset_.GetX() - x, 2) + pow(curPointerOffset_.GetY() - y, 2));
1791 CHECK_NULL_RETURN(info_.imageNode, distance);
1792 auto containerId = Container::CurrentId();
1793 auto subwindow = SubwindowManager::GetInstance()->GetSubwindow(containerId);
1794 CHECK_NULL_RETURN(subwindow, distance);
1795 auto overlayManager = subwindow->GetOverlayManager();
1796 auto gatherNodeCenter = info_.imageNode->GetPaintRectCenter();
1797 auto gatherDistance = CalcGatherNodeMaxDistanceWithPoint(overlayManager,
1798 gatherNodeCenter.GetX(), gatherNodeCenter.GetY());
1799 return std::max(distance, gatherDistance);
1800 }
1801
DoDragMoveAnimate(const DragPointerEvent & pointerEvent)1802 void DragDropManager::DoDragMoveAnimate(const DragPointerEvent& pointerEvent)
1803 {
1804 bool needDoDragMoveAnimate = IsNeedDoDragMoveAnimate(pointerEvent);
1805 if (!needDoDragMoveAnimate) {
1806 return;
1807 }
1808 isPullMoveReceivedForCurrentDrag_ = true;
1809 CHECK_NULL_VOID(info_.imageNode);
1810 auto containerId = Container::CurrentId();
1811 auto overlayManager = GetDragAnimationOverlayManager(containerId);
1812 CHECK_NULL_VOID(overlayManager);
1813 auto point = pointerEvent.GetPoint();
1814 Offset newOffset = CalcDragMoveOffset(PRESERVE_HEIGHT, point.GetX(), point.GetY(), info_);
1815 bool isMenuShow = overlayManager->IsMenuShow();
1816 if (UpdateDragMovePositionFinished(needDoDragMoveAnimate, isMenuShow, newOffset, containerId) ||
1817 !needDoDragMoveAnimate) {
1818 return;
1819 }
1820 DragMoveAnimation(newOffset, overlayManager, point);
1821 }
1822
DragMoveAnimation(const Offset & newOffset,const RefPtr<OverlayManager> & overlayManager,Point point)1823 void DragDropManager::DragMoveAnimation(
1824 const Offset& newOffset, const RefPtr<OverlayManager>& overlayManager, Point point)
1825 {
1826 auto containerId = Container::CurrentId();
1827 bool isMenuShow = overlayManager->IsMenuShow();
1828 AnimationOption option;
1829 auto springResponse =
1830 std::max(DEFAULT_SPRING_RESPONSE - DEL_SPRING_RESPONSE * allAnimationCnt_, MIN_SPRING_RESPONSE);
1831 const RefPtr<Curve> curve = AceType::MakeRefPtr<ResponsiveSpringMotion>(springResponse, 0.99f, 0.0f);
1832 constexpr int32_t animateDuration = 30;
1833 option.SetCurve(curve);
1834 option.SetDuration(animateDuration);
1835 bool dragWithContextMenu = isDragWithContextMenu_;
1836 AddNewDragAnimation();
1837 option.SetOnFinishEvent([weakManager = WeakClaim(this), containerId, dragWithContextMenu, isMenuShow,
1838 x = point.GetX(), y = point.GetY()]() {
1839 auto dragDropManager = weakManager.Upgrade();
1840 CHECK_NULL_VOID(dragDropManager);
1841 if ((dragDropManager->IsAllAnimationFinished() ||
1842 dragDropManager->GetCurrentDistance(x, y) < MAX_DISTANCE_TO_PRE_POINTER) &&
1843 (!dragWithContextMenu || !isMenuShow)) {
1844 dragDropManager->TransDragWindowToDragFwk(containerId);
1845 }
1846 });
1847 auto renderContext = info_.imageNode->GetRenderContext();
1848 CHECK_NULL_VOID(renderContext);
1849 auto offset = OffsetF(point.GetX(), point.GetY());
1850 auto menuWrapperNode = GetMenuWrapperNodeFromDrag();
1851 auto menuPosition = overlayManager->CalculateMenuPosition(menuWrapperNode, offset);
1852 auto menuRenderContext = GetMenuRenderContextFromMenuWrapper(menuWrapperNode);
1853 AnimationUtils::Animate(
1854 option,
1855 [renderContext, localPoint = newOffset, info = info_, overlayManager, menuRenderContext, menuPosition]() {
1856 if (menuRenderContext && !menuPosition.NonOffset()) {
1857 menuRenderContext->UpdatePosition(
1858 OffsetT<Dimension>(Dimension(menuPosition.GetX()), Dimension(menuPosition.GetY())));
1859 }
1860 renderContext->UpdateTransformTranslate({ localPoint.GetX(), localPoint.GetY(), 0.0f });
1861 UpdateGatherNodePosition(overlayManager, info.imageNode);
1862 UpdateTextNodePosition(info.textNode, localPoint);
1863 },
1864 option.GetOnFinishEvent());
1865 }
1866
UpdateDragPreviewScale()1867 void DragDropManager::UpdateDragPreviewScale()
1868 {
1869 CHECK_NULL_VOID(info_.imageNode);
1870 if (IsNeedDisplayInSubwindow()) {
1871 return;
1872 }
1873 auto renderContext = info_.imageNode->GetRenderContext();
1874 CHECK_NULL_VOID(renderContext);
1875 renderContext->UpdateTransformScale({ info_.scale, info_.scale });
1876 }
1877
DoDragStartAnimation(const RefPtr<OverlayManager> & overlayManager,const GestureEvent & event,const RefPtr<GestureEventHub> & gestureHub,bool isSubwindowOverlay)1878 void DragDropManager::DoDragStartAnimation(const RefPtr<OverlayManager>& overlayManager,
1879 const GestureEvent& event, const RefPtr<GestureEventHub>& gestureHub, bool isSubwindowOverlay)
1880 {
1881 auto containerId = Container::CurrentId();
1882 auto deviceId = static_cast<int32_t>(event.GetDeviceId());
1883 if (deviceId == RESERVED_DEVICEID_1 || deviceId == RESERVED_DEVICEID_2) {
1884 isDragFwkShow_ = false;
1885 TAG_LOGI(AceLogTag::ACE_DRAG, "Do not need animation.");
1886 TransDragWindowToDragFwk(containerId);
1887 return;
1888 }
1889 CHECK_NULL_VOID(overlayManager);
1890 CHECK_NULL_VOID(gestureHub);
1891 if (!(GetDragPreviewInfo(overlayManager, info_, gestureHub))
1892 || (!IsNeedDisplayInSubwindow() && !isSubwindowOverlay && !isDragWithContextMenu_)) {
1893 if (isDragWithContextMenu_) {
1894 UpdateDragPreviewScale();
1895 isDragFwkShow_ = false;
1896 }
1897 return;
1898 }
1899 CHECK_NULL_VOID(info_.imageNode);
1900 isDragFwkShow_ = false;
1901 ResetPullMoveReceivedForCurrentDrag();
1902 auto gatherNodeCenter = info_.imageNode->GetPaintRectCenter();
1903 Point point = { static_cast<int32_t>(event.GetGlobalLocation().GetX()),
1904 static_cast<int32_t>(event.GetGlobalLocation().GetY()) };
1905 Offset newOffset = CalcDragMoveOffset(PRESERVE_HEIGHT, static_cast<int32_t>(event.GetGlobalLocation().GetX()),
1906 static_cast<int32_t>(event.GetGlobalLocation().GetY()), info_);
1907 curPointerOffset_ = { newOffset.GetX(), newOffset.GetY() };
1908 currentAnimationCnt_ = 0;
1909 allAnimationCnt_ = 0;
1910 DragStartAnimation(newOffset, overlayManager, gatherNodeCenter, point);
1911 }
1912
DragStartAnimation(const Offset & newOffset,const RefPtr<OverlayManager> & overlayManager,const OffsetF & gatherNodeCenter,Point point)1913 void DragDropManager::DragStartAnimation(
1914 const Offset& newOffset, const RefPtr<OverlayManager>& overlayManager, const OffsetF& gatherNodeCenter, Point point)
1915 {
1916 auto containerId = Container::CurrentId();
1917 AnimationOption option;
1918 const RefPtr<Curve> curve = AceType::MakeRefPtr<ResponsiveSpringMotion>(0.347f, 0.99f, 0.0f);
1919 constexpr int32_t animateDuration = 300;
1920 option.SetCurve(curve);
1921 option.SetDuration(animateDuration);
1922 option.SetOnFinishEvent([weakManager = WeakClaim(this), containerId]() {
1923 auto dragDropManager = weakManager.Upgrade();
1924 if (dragDropManager && !dragDropManager->IsPullMoveReceivedForCurrentDrag()) {
1925 dragDropManager->TransDragWindowToDragFwk(containerId);
1926 }
1927 });
1928 auto renderContext = info_.imageNode->GetRenderContext();
1929 CHECK_NULL_VOID(renderContext);
1930 auto offset = OffsetF(point.GetX(), point.GetY());
1931 auto menuWrapperNode = GetMenuWrapperNodeFromDrag();
1932 auto menuPosition = overlayManager->CalculateMenuPosition(menuWrapperNode, offset);
1933 auto menuRenderContext = GetMenuRenderContextFromMenuWrapper(menuWrapperNode);
1934 AnimationUtils::Animate(
1935 option,
1936 [renderContext, info = info_, newOffset, overlayManager, gatherNodeCenter, menuRenderContext, menuPosition]() {
1937 CHECK_NULL_VOID(renderContext);
1938 if (menuRenderContext && !menuPosition.NonOffset()) {
1939 menuRenderContext->UpdatePosition(
1940 OffsetT<Dimension>(Dimension(menuPosition.GetX()), Dimension(menuPosition.GetY())));
1941 }
1942 renderContext->UpdateTransformScale({ info.scale, info.scale });
1943 renderContext->UpdateTransformTranslate({ newOffset.GetX(), newOffset.GetY(), 0.0f });
1944 GatherAnimationInfo gatherAnimationInfo = { info.scale, info.width, info.height,
1945 gatherNodeCenter, renderContext->GetBorderRadius() };
1946 UpdateGatherNodeAttr(overlayManager, gatherAnimationInfo);
1947 UpdateTextNodePosition(info.textNode, newOffset);
1948 },
1949 option.GetOnFinishEvent());
1950 }
1951
SetDragResult(const DragNotifyMsgCore & notifyMessage,const RefPtr<OHOS::Ace::DragEvent> & dragEvent)1952 void DragDropManager::SetDragResult(
1953 const DragNotifyMsgCore& notifyMessage, const RefPtr<OHOS::Ace::DragEvent>& dragEvent)
1954 {
1955 DragRet result = DragRet::DRAG_FAIL;
1956 switch (notifyMessage.result) {
1957 case DragRet::DRAG_SUCCESS:
1958 result = DragRet::DRAG_SUCCESS;
1959 break;
1960 case DragRet::DRAG_FAIL:
1961 result = DragRet::DRAG_FAIL;
1962 break;
1963 case DragRet::DRAG_CANCEL:
1964 result = DragRet::DRAG_CANCEL;
1965 break;
1966 default:
1967 break;
1968 }
1969 CHECK_NULL_VOID(dragEvent);
1970 dragEvent->SetResult(result);
1971 }
1972
SetDragBehavior(const DragNotifyMsgCore & notifyMessage,const RefPtr<OHOS::Ace::DragEvent> & dragEvent)1973 void DragDropManager::SetDragBehavior(
1974 const DragNotifyMsgCore& notifyMessage, const RefPtr<OHOS::Ace::DragEvent>& dragEvent)
1975 {
1976 DragBehavior dragBehavior = DragBehavior::UNKNOWN;
1977 switch (notifyMessage.dragBehavior) {
1978 case DragBehavior::COPY:
1979 dragBehavior = DragBehavior::COPY;
1980 break;
1981 case DragBehavior::MOVE:
1982 dragBehavior = DragBehavior::MOVE;
1983 break;
1984 default:
1985 break;
1986 }
1987 CHECK_NULL_VOID(dragEvent);
1988 dragEvent->SetDragBehavior(dragBehavior);
1989 }
1990
UpdateGatherNodeAttr(const RefPtr<OverlayManager> & overlayManager,const GatherAnimationInfo & info)1991 void DragDropManager::UpdateGatherNodeAttr(const RefPtr<OverlayManager>& overlayManager,
1992 const GatherAnimationInfo& info)
1993 {
1994 CHECK_NULL_VOID(overlayManager);
1995 auto gatherNodeChildrenInfo = overlayManager->GetGatherNodeChildrenInfo();
1996 BorderRadiusProperty borderRadius;
1997 if (info.borderRadius.has_value()) {
1998 borderRadius = info.borderRadius.value();
1999 }
2000 borderRadius.multiValued = false;
2001 int32_t cnt = static_cast<int>(gatherNodeChildrenInfo.size());
2002 auto scale = info.scale <= 0.0f ? 1.0f : info.scale;
2003 std::vector<std::pair<float, float>> props(cnt, { 0.0, 0.0 });
2004 if (cnt > 0) {
2005 props[cnt - FIRST_GATHER_PIXEL_MAP] = { FIRST_PIXELMAP_ANGLE, FIRST_PIXELMAP_OPACITY };
2006 }
2007 if (cnt > 1) {
2008 props[cnt - SECOND_GATHER_PIXEL_MAP] = { SECOND_PIXELMAP_ANGLE, SECOND_PIXELMAP_OPACITY };
2009 }
2010 for (int32_t i = 0; i < cnt; ++i) {
2011 auto imageNode = gatherNodeChildrenInfo[i].imageNode.Upgrade();
2012 CHECK_NULL_VOID(imageNode);
2013 auto imageContext = imageNode->GetRenderContext();
2014 CHECK_NULL_VOID(imageContext);
2015 auto& childInfo = gatherNodeChildrenInfo[i];
2016 imageContext->UpdatePosition(OffsetT<Dimension>(
2017 Dimension(info.gatherNodeCenter.GetX() - childInfo.halfWidth),
2018 Dimension(info.gatherNodeCenter.GetY() - childInfo.halfHeight)));
2019 auto updateScale = scale;
2020 if (((childInfo.width > info.width) || (childInfo.height > info.height)) &&
2021 !NearZero(childInfo.width) && !NearZero(childInfo.height)) {
2022 updateScale *= std::min(info.width / childInfo.width, info.height / childInfo.height);
2023 }
2024 imageContext->UpdateTransformScale({ updateScale, updateScale });
2025 imageContext->UpdateBorderRadius(borderRadius);
2026 imageContext->UpdateOpacity(props[i].second);
2027 Vector5F rotate = Vector5F(0.0f, 0.0f, 1.0f, props[i].first, 0.0f);
2028 imageContext->UpdateTransformRotate(rotate);
2029 }
2030 }
2031
UpdateGatherNodePosition(const RefPtr<OverlayManager> & overlayManager,const RefPtr<FrameNode> & imageNode)2032 void DragDropManager::UpdateGatherNodePosition(const RefPtr<OverlayManager>& overlayManager,
2033 const RefPtr<FrameNode>& imageNode)
2034 {
2035 CHECK_NULL_VOID(imageNode);
2036 auto gatherNodeCenter = imageNode->GetPaintRectCenter();
2037 CHECK_NULL_VOID(overlayManager);
2038 Dimension x = Dimension(0.0f);
2039 Dimension y = Dimension(0.0f);
2040 OffsetT<Dimension> offset(x, y);
2041 auto gatherNodeChildrenInfo = overlayManager->GetGatherNodeChildrenInfo();
2042 for (const auto& child : gatherNodeChildrenInfo) {
2043 auto imageNode = child.imageNode.Upgrade();
2044 CHECK_NULL_VOID(imageNode);
2045 auto imageContext = imageNode->GetRenderContext();
2046 CHECK_NULL_VOID(imageContext);
2047 x.SetValue(gatherNodeCenter.GetX() - child.halfWidth);
2048 y.SetValue(gatherNodeCenter.GetY() - child.halfHeight);
2049 offset.SetX(x);
2050 offset.SetY(y);
2051 imageContext->UpdatePosition(offset);
2052 }
2053 }
2054
UpdateTextNodePosition(const RefPtr<FrameNode> & textNode,const Offset & localPoint)2055 void DragDropManager::UpdateTextNodePosition(const RefPtr<FrameNode>& textNode, const Offset& localPoint)
2056 {
2057 CHECK_NULL_VOID(textNode);
2058 auto textRenderContext = textNode->GetRenderContext();
2059 CHECK_NULL_VOID(textRenderContext);
2060 textRenderContext->UpdateTransformTranslate({ localPoint.GetX(), localPoint.GetY(), 0.0f });
2061 }
2062
CalcGatherNodeMaxDistanceWithPoint(const RefPtr<OverlayManager> & overlayManager,int32_t x,int32_t y)2063 double DragDropManager::CalcGatherNodeMaxDistanceWithPoint(const RefPtr<OverlayManager>& overlayManager,
2064 int32_t x, int32_t y)
2065 {
2066 CHECK_NULL_RETURN(overlayManager, 0.0f);
2067 auto gatherNodeChildrenInfo = overlayManager->GetGatherNodeChildrenInfo();
2068 double maxDistance = 0.0;
2069 for (const auto& child : gatherNodeChildrenInfo) {
2070 auto imageNode = child.imageNode.Upgrade();
2071 CHECK_NULL_RETURN(imageNode, 0.0f);
2072 auto imageContext = imageNode->GetRenderContext();
2073 CHECK_NULL_RETURN(imageContext, 0.0f);
2074 auto renderPosition = imageContext->GetPropertyOfPosition();
2075 double dis = sqrt(pow(renderPosition.GetX() + child.halfWidth - x, SQUARE_NUMBER) +
2076 pow(renderPosition.GetY() + child.halfHeight - y, SQUARE_NUMBER));
2077 maxDistance = std::max(maxDistance, dis);
2078 }
2079 return maxDistance;
2080 }
2081
IsNeedDisplayInSubwindow()2082 bool DragDropManager::IsNeedDisplayInSubwindow()
2083 {
2084 if (IsNeedScaleDragPreview()) {
2085 return true;
2086 }
2087 auto overlayManager = GetDragAnimationOverlayManager(Container::CurrentId());
2088 CHECK_NULL_RETURN(overlayManager, false);
2089 auto gatherNode = overlayManager->GetGatherNode();
2090 return gatherNode != nullptr;
2091 }
2092
PushGatherPixelMap(const RefPtr<PixelMap> & pixelMap)2093 void DragDropManager::PushGatherPixelMap(const RefPtr<PixelMap>& pixelMap)
2094 {
2095 gatherPixelMaps_.push_back(pixelMap);
2096 }
2097
GetGatherPixelMap(DragDataCore & dragData,float scale,float previewWidth,float previewHeight)2098 void DragDropManager::GetGatherPixelMap(DragDataCore& dragData, float scale, float previewWidth, float previewHeight)
2099 {
2100 for (const auto& gatherPixelMap : gatherPixelMaps_) {
2101 RefPtr<PixelMap> pixelMapDuplicated = gatherPixelMap;
2102 #if defined(PIXEL_MAP_SUPPORTED)
2103 pixelMapDuplicated = PixelMap::CopyPixelMap(gatherPixelMap);
2104 if (!pixelMapDuplicated) {
2105 TAG_LOGW(AceLogTag::ACE_DRAG, "Copy PixelMap is failure!");
2106 pixelMapDuplicated = gatherPixelMap;
2107 }
2108 #endif
2109 auto width = pixelMapDuplicated->GetWidth() * scale;
2110 auto height = pixelMapDuplicated->GetHeight() * scale;
2111 auto updateScale = scale;
2112 if (((width > previewWidth) || (height > previewHeight)) && !NearZero(width) && !NearZero(height)) {
2113 updateScale *= std::min(previewWidth / width, previewHeight / height);
2114 }
2115 pixelMapDuplicated->Scale(updateScale, updateScale, AceAntiAliasingOption::HIGH);
2116 dragData.shadowInfos.push_back({pixelMapDuplicated, 0.0f, 0.0f});
2117 }
2118 gatherPixelMaps_.clear();
2119 return;
2120 }
2121
ResetDragDrop(int32_t windowId,const Point & point)2122 void DragDropManager::ResetDragDrop(int32_t windowId, const Point& point)
2123 {
2124 DragDropRet dragDropRet { DragRet::DRAG_FAIL, isMouseDragged_, windowId, DragBehavior::UNKNOWN };
2125 HideDragPreviewOverlay();
2126 ClearVelocityInfo();
2127 ResetDragDropStatus(point, dragDropRet, windowId);
2128 dragCursorStyleCore_ = DragCursorStyleCore::DEFAULT;
2129 }
2130
FireOnDragLeave(const RefPtr<FrameNode> & preTargetFrameNode,const DragPointerEvent & pointerEvent,const std::string & extraInfo)2131 void DragDropManager::FireOnDragLeave(
2132 const RefPtr<FrameNode>& preTargetFrameNode, const DragPointerEvent& pointerEvent, const std::string& extraInfo)
2133 {
2134 auto point = pointerEvent.GetPoint();
2135 if (preTargetFrameNode) {
2136 auto preRect = preTargetFrameNode->GetTransformRectRelativeToWindow();
2137 // If the point is out of the pre node, it means we are totally inside a new node, notify leave anyway
2138 if (!preRect.IsInnerRegion(PointF(static_cast<float>(point.GetX()), static_cast<float>(point.GetY())))) {
2139 FireOnDragEvent(preTargetFrameNode, pointerEvent, DragEventType::LEAVE, extraInfo);
2140 return;
2141 }
2142
2143 // If reach here, it means we are entering one new node's area, but without leaving the area of the pre
2144 // one, this usually happens when moving from parent into its child.
2145 // Check the configuration to decide the notify to parent node.
2146 if (eventStrictReportingEnabled_) {
2147 FireOnDragEvent(preTargetFrameNode_, pointerEvent, DragEventType::LEAVE, extraInfo);
2148 }
2149 }
2150 }
2151
IsUIExtensionShowPlaceholder(const RefPtr<NG::UINode> & node)2152 bool DragDropManager::IsUIExtensionShowPlaceholder(const RefPtr<NG::UINode>& node)
2153 {
2154 #ifdef WINDOW_SCENE_SUPPORTED
2155 CHECK_NULL_RETURN(node, true);
2156 auto pipeline = PipelineContext::GetCurrentContext();
2157 CHECK_NULL_RETURN(pipeline, true);
2158 auto manager = pipeline->GetUIExtensionManager();
2159 CHECK_NULL_RETURN(manager, true);
2160 return manager->IsShowPlaceholder(node->GetId());
2161 #endif
2162 return true;
2163 }
2164
UpdateDragMovePosition(const NG::OffsetF & offset,bool isRedragStart)2165 void DragDropManager::UpdateDragMovePosition(const NG::OffsetF& offset, bool isRedragStart)
2166 {
2167 if (isRedragStart) {
2168 ResetContextMenuRedragPosition();
2169 }
2170 lastDragMovePosition_ = dragMovePosition_;
2171 dragMovePosition_ = offset;
2172 if (lastDragMovePosition_.NonOffset()) {
2173 return;
2174 }
2175 dragTotalMovePosition_ += (dragMovePosition_ - lastDragMovePosition_);
2176 }
2177
IsUIExtensionComponent(const RefPtr<NG::UINode> & node)2178 bool DragDropManager::IsUIExtensionComponent(const RefPtr<NG::UINode>& node)
2179 {
2180 return (V2::UI_EXTENSION_COMPONENT_ETS_TAG == node->GetTag() || V2::EMBEDDED_COMPONENT_ETS_TAG == node->GetTag()) &&
2181 (!IsUIExtensionShowPlaceholder(node));
2182 }
2183
GetMenuPreviewRect()2184 RectF DragDropManager::GetMenuPreviewRect()
2185 {
2186 auto pipelineContext = PipelineContext::GetCurrentContext();
2187 CHECK_NULL_RETURN(pipelineContext, RectF());
2188 auto dragDropManager = pipelineContext->GetDragDropManager();
2189 CHECK_NULL_RETURN(dragDropManager, RectF());
2190 auto menuWrapperNode = dragDropManager->GetMenuWrapperNode();
2191 CHECK_NULL_RETURN(menuWrapperNode, RectF());
2192 auto menuWrapperPattern = menuWrapperNode->GetPattern<MenuWrapperPattern>();
2193 CHECK_NULL_RETURN(menuWrapperPattern, RectF());
2194 auto menuPreview = menuWrapperPattern->GetPreview();
2195 CHECK_NULL_RETURN(menuPreview, RectF());
2196 auto menuRenderContext = menuPreview->GetRenderContext();
2197 CHECK_NULL_RETURN(menuRenderContext, RectF());
2198 auto previewPaintRect = menuRenderContext->GetPaintRectWithTransform();
2199 return previewPaintRect;
2200 }
2201
GetMaxWidthBaseOnGridSystem(const RefPtr<PipelineBase> & pipeline)2202 double DragDropManager::GetMaxWidthBaseOnGridSystem(const RefPtr<PipelineBase>& pipeline)
2203 {
2204 auto context = DynamicCast<NG::PipelineContext>(pipeline);
2205 CHECK_NULL_RETURN(context, -1.0f);
2206 auto dragDropMgr = context->GetDragDropManager();
2207 CHECK_NULL_RETURN(dragDropMgr, -1.0f);
2208 auto& columnInfo = dragDropMgr->columnInfo_;
2209 if (!columnInfo) {
2210 columnInfo = GridSystemManager::GetInstance().GetInfoByType(GridColumnType::DRAG_PANEL);
2211 auto gridContainer = columnInfo->GetParent();
2212 if (gridContainer) {
2213 auto rootWidth = context->GetRootWidth();
2214 if (LessOrEqual(rootWidth, 0.0)) {
2215 auto mainPipeline = PipelineContext::GetMainPipelineContext();
2216 rootWidth = GridSystemManager::GetInstance().GetScreenWidth(mainPipeline);
2217 }
2218 // cannot handle multi-screen
2219 gridContainer->BuildColumnWidth(rootWidth);
2220 }
2221 dragDropMgr->columnInfo_ = columnInfo;
2222 }
2223
2224 auto gridSizeType = GridSystemManager::GetInstance().GetCurrentSize();
2225 if (gridSizeType > GridSizeType::LG) {
2226 gridSizeType = GridSizeType::LG;
2227 }
2228 if (gridSizeType < GridSizeType::SM) {
2229 gridSizeType = GridSizeType::SM;
2230 }
2231 auto columns = columnInfo->GetColumns(gridSizeType);
2232 double maxWidth = columnInfo->GetWidth(columns);
2233 return maxWidth;
2234 }
2235
GetDragAnimationOverlayManager(int32_t containerId)2236 const RefPtr<NG::OverlayManager> DragDropManager::GetDragAnimationOverlayManager(int32_t containerId)
2237 {
2238 auto subwindow = SubwindowManager::GetInstance()->GetSubwindow(containerId >= MIN_SUBCONTAINER_ID ?
2239 SubwindowManager::GetInstance()->GetParentContainerId(containerId) : containerId);
2240 CHECK_NULL_RETURN(subwindow, nullptr);
2241 return subwindow->GetOverlayManager();
2242 }
2243
RemoveDragFrameNode(int32_t id)2244 void DragDropManager::RemoveDragFrameNode(int32_t id)
2245 {
2246 dragFrameNodes_.erase(id);
2247 gridDragFrameNodes_.erase(id);
2248 listDragFrameNodes_.erase(id);
2249 textFieldDragFrameNodes_.erase(id);
2250 }
2251
SetIsDragged(bool isDragged)2252 void DragDropManager::SetIsDragged(bool isDragged)
2253 {
2254 if (isDragged && isDragged_ != isDragged && notifyInDraggedCallback_) {
2255 notifyInDraggedCallback_();
2256 }
2257 isDragged_ = isDragged;
2258 }
2259
RegisterDragStatusListener(int32_t nodeId,const WeakPtr<FrameNode> & node)2260 void DragDropManager::RegisterDragStatusListener(int32_t nodeId, const WeakPtr<FrameNode>& node)
2261 {
2262 auto ret = nodesForDragNotify_.try_emplace(nodeId, node);
2263 if (!ret.second) {
2264 nodesForDragNotify_[nodeId] = node;
2265 }
2266 }
2267
IsDraggingPressed(int32_t currentPointerId) const2268 bool DragDropManager::IsDraggingPressed(int32_t currentPointerId) const
2269 {
2270 if (currentPointerId_ == currentPointerId) {
2271 return draggingPressedState_;
2272 }
2273 return false;
2274 }
2275
ResetContextMenuDragPosition()2276 void DragDropManager::ResetContextMenuDragPosition()
2277 {
2278 dragMovePosition_ = OffsetF(0.0f, 0.0f);
2279 lastDragMovePosition_ = OffsetF(0.0f, 0.0f);
2280 dragTotalMovePosition_ = OffsetF(0.0f, 0.0f);
2281 }
2282
ResetContextMenuRedragPosition()2283 void DragDropManager::ResetContextMenuRedragPosition()
2284 {
2285 dragMovePosition_ = OffsetF(0.0f, 0.0f);
2286 lastDragMovePosition_ = OffsetF(0.0f, 0.0f);
2287 }
2288
AddNewDragAnimation()2289 void DragDropManager::AddNewDragAnimation()
2290 {
2291 currentAnimationCnt_++;
2292 allAnimationCnt_++;
2293 }
2294
IsAllAnimationFinished()2295 bool DragDropManager::IsAllAnimationFinished()
2296 {
2297 currentAnimationCnt_--;
2298 return currentAnimationCnt_ == 0;
2299 }
2300
CheckIsNewDrag(const DragPointerEvent & pointerEvent) const2301 bool DragDropManager::CheckIsNewDrag(const DragPointerEvent& pointerEvent) const
2302 {
2303 return (pointerEvent.pullId != -1) && (pointerEvent.pullId != currentPullId_);
2304 }
2305
RequireSummaryIfNecessary(const DragPointerEvent & pointerEvent)2306 void DragDropManager::RequireSummaryIfNecessary(const DragPointerEvent& pointerEvent)
2307 {
2308 if (CheckIsNewDrag(pointerEvent)) {
2309 currentPullId_ = pointerEvent.pullId;
2310 RequireSummary();
2311 }
2312 }
2313
CancelUDMFDataLoading(const std::string & key)2314 int32_t DragDropManager::CancelUDMFDataLoading(const std::string& key)
2315 {
2316 return UdmfClient::GetInstance()->Cancel(key);
2317 }
2318 } // namespace OHOS::Ace::NG
2319