1 /*
2 * Copyright (c) 2022 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/event/drag_event.h"
17
18 #include "base/utils/system_properties.h"
19 #include "base/utils/utils.h"
20 #include "core/common/container.h"
21 #include "core/common/interaction/interaction_data.h"
22 #include "core/common/interaction/interaction_interface.h"
23 #include "core/components/common/layout/constants.h"
24 #include "core/components_ng/base/frame_node.h"
25 #include "core/components_ng/event/gesture_event_hub.h"
26 #include "core/components_ng/event/gesture_info.h"
27 #include "core/components_ng/gestures/recognizers/long_press_recognizer.h"
28 #include "core/components_ng/gestures/recognizers/pan_recognizer.h"
29 #include "core/components_ng/gestures/recognizers/sequenced_recognizer.h"
30 #include "core/pipeline_ng/pipeline_context.h"
31
32 #include "base/subwindow/subwindow_manager.h"
33 #include "core/animation/animation_pub.h"
34 #include "core/components/container_modal/container_modal_constants.h"
35 #include "core/components_ng/pattern/image/image_layout_property.h"
36 #include "core/components_ng/pattern/image/image_pattern.h"
37 #include "core/components_ng/pattern/linear_layout/linear_layout_pattern.h"
38 #include "core/components_ng/pattern/text/text_base.h"
39 #include "core/components_ng/pattern/text_drag/text_drag_base.h"
40 #include "core/components_ng/pattern/text_drag/text_drag_pattern.h"
41 #include "core/components_ng/render/adapter/component_snapshot.h"
42 #include "core/components_ng/render/render_context.h"
43 #include "core/components_v2/inspector/inspector_constants.h"
44
45 #ifdef WEB_SUPPORTED
46 #include "core/components_ng/pattern/web/web_pattern.h"
47 #endif // WEB_SUPPORTED
48
49 namespace OHOS::Ace::NG {
50 namespace {
51 constexpr int32_t PAN_FINGER = 1;
52 constexpr double PAN_DISTANCE = 5.0;
53 constexpr int32_t LONG_PRESS_DURATION = 500;
54 constexpr int32_t PREVIEW_LONG_PRESS_RECONGNIZER = 800;
55 constexpr Dimension FILTER_VALUE(0.0f);
56 constexpr float PIXELMAP_DRAG_SCALE_MULTIPLE = 1.05f;
57 constexpr int32_t PIXELMAP_ANIMATION_TIME = 800;
58 constexpr float SCALE_NUMBER = 0.95f;
59 constexpr int32_t FILTER_TIMES = 250;
60 constexpr float PIXELMAP_ANIMATION_SCALE = 1.1f;
61 constexpr int32_t PIXELMAP_ANIMATION_DURATION = 300;
62 constexpr float SPRING_RESPONSE = 0.416f;
63 constexpr float SPRING_DAMPING_FRACTION = 0.73f;
64 constexpr Dimension PIXELMAP_BORDER_RADIUS = 16.0_vp;
65 #if defined(PIXEL_MAP_SUPPORTED)
66 constexpr int32_t CREATE_PIXELMAP_TIME = 80;
67 #endif
68 } // namespace
69
DragEventActuator(const WeakPtr<GestureEventHub> & gestureEventHub,PanDirection direction,int32_t fingers,float distance)70 DragEventActuator::DragEventActuator(
71 const WeakPtr<GestureEventHub>& gestureEventHub, PanDirection direction, int32_t fingers, float distance)
72 : gestureEventHub_(gestureEventHub), direction_(direction), fingers_(fingers), distance_(distance)
73 {
74 if (fingers_ < PAN_FINGER) {
75 fingers_ = PAN_FINGER;
76 }
77
78 if (LessOrEqual(distance_, PAN_DISTANCE)) {
79 distance_ = PAN_DISTANCE;
80 }
81
82 panRecognizer_ = MakeRefPtr<PanRecognizer>(fingers_, direction_, distance_);
83 panRecognizer_->SetGestureInfo(MakeRefPtr<GestureInfo>(GestureTypeName::DRAG, true));
84 longPressRecognizer_ = AceType::MakeRefPtr<LongPressRecognizer>(LONG_PRESS_DURATION, fingers_, false, false);
85 longPressRecognizer_->SetGestureInfo(MakeRefPtr<GestureInfo>(GestureTypeName::DRAG, true));
86 previewLongPressRecognizer_ =
87 AceType::MakeRefPtr<LongPressRecognizer>(PREVIEW_LONG_PRESS_RECONGNIZER, fingers_, false, false);
88 previewLongPressRecognizer_->SetGestureInfo(MakeRefPtr<GestureInfo>(GestureTypeName::DRAG, true));
89 isNotInPreviewState_ = false;
90 }
91
StartDragTaskForWeb(const GestureEvent & info)92 void DragEventActuator::StartDragTaskForWeb(const GestureEvent& info)
93 {
94 auto gestureInfo = const_cast<GestureEvent&>(info);
95 if (actionStart_) {
96 actionStart_(gestureInfo);
97 }
98 }
99
StartLongPressActionForWeb()100 void DragEventActuator::StartLongPressActionForWeb()
101 {
102 if (!isReceivedLongPress_) {
103 TAG_LOGW(AceLogTag::ACE_DRAG, "not received long press action, don't start long press action for web");
104 return;
105 }
106 if (longPressUpdate_) {
107 longPressUpdate_(longPressInfo_);
108 }
109 isReceivedLongPress_ = false;
110 }
111
CancelDragForWeb()112 void DragEventActuator::CancelDragForWeb()
113 {
114 if (actionCancel_) {
115 actionCancel_();
116 }
117 }
118
OnCollectTouchTarget(const OffsetF & coordinateOffset,const TouchRestrict & touchRestrict,const GetEventTargetImpl & getEventTargetImpl,TouchTestResult & result)119 void DragEventActuator::OnCollectTouchTarget(const OffsetF& coordinateOffset, const TouchRestrict& touchRestrict,
120 const GetEventTargetImpl& getEventTargetImpl, TouchTestResult& result)
121 {
122 CHECK_NULL_VOID(userCallback_);
123 isDragUserReject_ = false;
124 auto gestureHub = gestureEventHub_.Upgrade();
125 CHECK_NULL_VOID(gestureHub);
126 auto frameNode = gestureHub->GetFrameNode();
127 CHECK_NULL_VOID(frameNode);
128 auto pipeline = PipelineContext::GetCurrentContext();
129 CHECK_NULL_VOID(pipeline);
130 auto dragDropManager = pipeline->GetDragDropManager();
131 CHECK_NULL_VOID(dragDropManager);
132 if (dragDropManager->IsDragging() || dragDropManager->IsMsdpDragging() ||
133 (!frameNode->IsDraggable() && frameNode->IsCustomerSet())) {
134 TAG_LOGI(AceLogTag::ACE_DRAG, "No need to collect drag gestures result, dragging is %{public}d,"
135 "MSDP dragging is %{public}d, frameNode draggable is %{public}d, custom set is %{public}d",
136 dragDropManager->IsDragging(), dragDropManager->IsMsdpDragging(),
137 frameNode->IsDraggable(), frameNode->IsCustomerSet());
138 return;
139 }
140 auto actionStart = [weak = WeakClaim(this), this](GestureEvent& info) {
141 auto actuator = weak.Upgrade();
142 CHECK_NULL_VOID(actuator);
143 auto pipeline = PipelineContext::GetCurrentContext();
144 CHECK_NULL_VOID(pipeline);
145 auto dragDropManager = pipeline->GetDragDropManager();
146 CHECK_NULL_VOID(dragDropManager);
147 dragDropManager->ResetDragging(DragDropMgrState::ABOUT_TO_PREVIEW);
148 auto gestureHub = actuator->gestureEventHub_.Upgrade();
149 CHECK_NULL_VOID(gestureHub);
150 auto frameNode = gestureHub->GetFrameNode();
151 CHECK_NULL_VOID(frameNode);
152 auto renderContext = frameNode->GetRenderContext();
153 if (info.GetSourceDevice() != SourceType::MOUSE) {
154 if (gestureHub->GetTextDraggable()) {
155 auto pattern = frameNode->GetPattern<TextBase>();
156 CHECK_NULL_VOID(pattern);
157 if (!pattern->IsSelected()) {
158 dragDropManager->ResetDragging();
159 gestureHub->SetIsTextDraggable(false);
160 return;
161 }
162 if (gestureHub->GetIsTextDraggable()) {
163 SetTextPixelMap(gestureHub);
164 } else {
165 gestureHub->SetPixelMap(nullptr);
166 }
167 } else if (!isNotInPreviewState_) {
168 if (gestureHub->GetTextDraggable()) {
169 HideTextAnimation(true, info.GetGlobalLocation().GetX(), info.GetGlobalLocation().GetY());
170 } else {
171 HideEventColumn();
172 HidePixelMap(true, info.GetGlobalLocation().GetX(), info.GetGlobalLocation().GetY());
173 HideFilter();
174 SubwindowManager::GetInstance()->HideMenuNG(false, true);
175 }
176 }
177 }
178
179 if (info.GetSourceDevice() == SourceType::MOUSE) {
180 frameNode->MarkModifyDone();
181 auto pattern = frameNode->GetPattern<TextBase>();
182 if (gestureHub->GetTextDraggable() && pattern) {
183 if (!pattern->IsSelected() || pattern->GetMouseStatus() == MouseStatus::MOVE) {
184 dragDropManager->ResetDragging();
185 gestureHub->SetIsTextDraggable(false);
186 return;
187 }
188 if (pattern->BetweenSelectedPosition(info.GetGlobalLocation())) {
189 gestureHub->SetIsTextDraggable(true);
190 if (textDragCallback_) {
191 textDragCallback_(info.GetGlobalLocation());
192 }
193 }
194 }
195 }
196
197 // Trigger drag start event set by user.
198 CHECK_NULL_VOID(actuator->userCallback_);
199 auto userActionStart = actuator->userCallback_->GetActionStartEventFunc();
200 if (userActionStart) {
201 TAG_LOGI(AceLogTag::ACE_DRAG, "Trigger drag start event set by user.");
202 userActionStart(info);
203 }
204 // Trigger custom drag start event
205 CHECK_NULL_VOID(actuator->customCallback_);
206 auto customActionStart = actuator->customCallback_->GetActionStartEventFunc();
207 if (customActionStart) {
208 customActionStart(info);
209 }
210 };
211 actionStart_ = actionStart;
212 panRecognizer_->SetOnActionStart(actionStart);
213
214 auto actionUpdate = [weak = WeakClaim(this)](GestureEvent& info) {
215 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent panRecognizer onActionUpdate.");
216 auto actuator = weak.Upgrade();
217 CHECK_NULL_VOID(actuator);
218 CHECK_NULL_VOID(actuator->userCallback_);
219 auto userActionUpdate = actuator->userCallback_->GetActionUpdateEventFunc();
220 if (userActionUpdate) {
221 userActionUpdate(info);
222 }
223 CHECK_NULL_VOID(actuator->customCallback_);
224 auto customActionUpdate = actuator->customCallback_->GetActionUpdateEventFunc();
225 if (customActionUpdate) {
226 customActionUpdate(info);
227 }
228 };
229 panRecognizer_->SetOnActionUpdate(actionUpdate);
230
231 auto actionEnd = [weak = WeakClaim(this)](GestureEvent& info) {
232 auto actuator = weak.Upgrade();
233 CHECK_NULL_VOID(actuator);
234 CHECK_NULL_VOID(actuator->userCallback_);
235 auto gestureHub = actuator->gestureEventHub_.Upgrade();
236 CHECK_NULL_VOID(gestureHub);
237 if (gestureHub->GetTextDraggable()) {
238 actuator->HideTextAnimation();
239 }
240 auto userActionEnd = actuator->userCallback_->GetActionEndEventFunc();
241 if (userActionEnd) {
242 TAG_LOGI(AceLogTag::ACE_DRAG, "Trigger drag end event set by user.");
243 userActionEnd(info);
244 }
245 CHECK_NULL_VOID(actuator->customCallback_);
246 auto customActionEnd = actuator->customCallback_->GetActionEndEventFunc();
247 if (customActionEnd) {
248 customActionEnd(info);
249 }
250 actuator->SetIsNotInPreviewState(false);
251 };
252 panRecognizer_->SetOnActionEnd(actionEnd);
253 auto actionCancel = [weak = WeakClaim(this), this]() {
254 TAG_LOGD(AceLogTag::ACE_DRAG, "Drag event has been canceled.");
255 auto actuator = weak.Upgrade();
256 CHECK_NULL_VOID(actuator);
257 auto gestureHub = actuator->gestureEventHub_.Upgrade();
258 CHECK_NULL_VOID(gestureHub);
259 if (!GetIsBindOverlayValue(actuator)) {
260 if (gestureHub->GetTextDraggable()) {
261 if (gestureHub->GetIsTextDraggable()) {
262 HideTextAnimation();
263 }
264 } else {
265 auto frameNode = gestureHub->GetFrameNode();
266 CHECK_NULL_VOID(frameNode);
267 auto renderContext = frameNode->GetRenderContext();
268 BorderRadiusProperty borderRadius;
269 if (renderContext->GetBorderRadius().has_value()) {
270 borderRadius.UpdateWithCheck(renderContext->GetBorderRadius().value());
271 }
272 borderRadius.multiValued = false;
273 AnimationOption option;
274 option.SetDuration(PIXELMAP_ANIMATION_DURATION);
275 option.SetCurve(Curves::FRICTION);
276 AnimationUtils::Animate(
277 option,
278 [renderContext_ = renderContext, borderRadius_ = borderRadius]() {
279 renderContext_->UpdateBorderRadius(borderRadius_);
280 },
281 option.GetOnFinishEvent());
282 HidePixelMap();
283 HideFilter();
284 }
285 } else {
286 if (actuator->panRecognizer_->getDeviceType() == SourceType::MOUSE) {
287 if (!gestureHub->GetTextDraggable()) {
288 HideEventColumn();
289 HidePixelMap();
290 HideFilter();
291 }
292 }
293 }
294 actuator->SetIsNotInPreviewState(false);
295 CHECK_NULL_VOID(actuator->userCallback_);
296 auto userActionCancel = actuator->userCallback_->GetActionCancelEventFunc();
297 if (userActionCancel) {
298 userActionCancel();
299 }
300 CHECK_NULL_VOID(actuator->customCallback_);
301 auto customActionCancel = actuator->customCallback_->GetActionCancelEventFunc();
302 if (customActionCancel) {
303 customActionCancel();
304 }
305 };
306 panRecognizer_->SetIsForDrag(true);
307 panRecognizer_->SetMouseDistance(DRAG_PAN_DISTANCE_MOUSE.ConvertToPx());
308 actionCancel_ = actionCancel;
309 panRecognizer_->SetCoordinateOffset(Offset(coordinateOffset.GetX(), coordinateOffset.GetY()));
310 panRecognizer_->SetOnActionCancel(actionCancel);
311 if (touchRestrict.sourceType == SourceType::MOUSE) {
312 std::vector<RefPtr<NGGestureRecognizer>> recognizers { panRecognizer_ };
313 SequencedRecognizer_ = AceType::MakeRefPtr<SequencedRecognizer>(recognizers);
314 SequencedRecognizer_->RemainChildOnResetStatus();
315 SequencedRecognizer_->SetCoordinateOffset(Offset(coordinateOffset.GetX(), coordinateOffset.GetY()));
316 SequencedRecognizer_->SetGetEventTargetImpl(getEventTargetImpl);
317 result.emplace_back(SequencedRecognizer_);
318 return;
319 }
320 auto longPressUpdateValue = [weak = WeakClaim(this)](GestureEvent& info) {
321 TAG_LOGD(AceLogTag::ACE_DRAG, "Trigger long press for 500ms.");
322 auto actuator = weak.Upgrade();
323 CHECK_NULL_VOID(actuator);
324 actuator->SetIsNotInPreviewState(true);
325 };
326 longPressRecognizer_->SetOnActionUpdate(longPressUpdateValue);
327 auto longPressUpdate = [weak = WeakClaim(this)](GestureEvent& info) {
328 TAG_LOGI(AceLogTag::ACE_DRAG, "Trigger long press for 800ms.");
329 auto pipeline = PipelineContext::GetCurrentContext();
330 CHECK_NULL_VOID(pipeline);
331
332 auto overlayManager = pipeline->GetOverlayManager();
333 CHECK_NULL_VOID(overlayManager);
334 if (overlayManager->GetHasPixelMap()) {
335 return;
336 }
337
338 auto dragDropManager = pipeline->GetDragDropManager();
339 CHECK_NULL_VOID(dragDropManager);
340 if (dragDropManager->IsAboutToPreview() || dragDropManager->IsDragging()) {
341 return;
342 }
343 auto actuator = weak.Upgrade();
344 CHECK_NULL_VOID(actuator);
345 auto gestureHub = actuator->gestureEventHub_.Upgrade();
346 CHECK_NULL_VOID(gestureHub);
347 if (gestureHub->GetTextDraggable()) {
348 actuator->SetIsNotInPreviewState(false);
349 if (gestureHub->GetIsTextDraggable()) {
350 actuator->SetTextAnimation(gestureHub, info.GetGlobalLocation());
351 }
352 return;
353 }
354
355 bool isAllowedDrag = actuator->IsAllowedDrag();
356 if (!isAllowedDrag) {
357 actuator->longPressInfo_ = info;
358 actuator->isReceivedLongPress_ = true;
359 return;
360 }
361
362 actuator->SetFilter(actuator);
363 auto manager = pipeline->GetOverlayManager();
364 CHECK_NULL_VOID(manager);
365 actuator->SetIsNotInPreviewState(false);
366 actuator->SetPixelMap(actuator);
367 auto motion = AceType::MakeRefPtr<ResponsiveSpringMotion>(SPRING_RESPONSE, SPRING_DAMPING_FRACTION, 0);
368 auto column = manager->GetPixelMapNode();
369 CHECK_NULL_VOID(column);
370
371 auto imageNode = AceType::DynamicCast<FrameNode>(column->GetFirstChild());
372 CHECK_NULL_VOID(imageNode);
373 auto imageContext = imageNode->GetRenderContext();
374 CHECK_NULL_VOID(imageContext);
375 if (gestureHub->GetPreviewMode() == MenuPreviewMode::NONE) {
376 AnimationOption option;
377 option.SetDuration(PIXELMAP_ANIMATION_TIME);
378 option.SetCurve(motion);
379 AnimationUtils::Animate(
380 option,
381 [imageContext]() {
382 imageContext->UpdateTransformScale({ PIXELMAP_DRAG_SCALE_MULTIPLE, PIXELMAP_DRAG_SCALE_MULTIPLE });
383 },
384 option.GetOnFinishEvent());
385 } else {
386 imageContext->UpdateOpacity(0.0);
387 }
388 actuator->SetEventColumn(actuator);
389 };
390 auto longPressCancel = [weak = WeakClaim(this)] {
391 // remove drag overlay info by Cancel event.
392 TAG_LOGD(AceLogTag::ACE_DRAG, "Long press event has been canceled.");
393 auto actuator = weak.Upgrade();
394 CHECK_NULL_VOID(actuator);
395 actuator->HideEventColumn();
396 actuator->HidePixelMap();
397 actuator->HideFilter();
398 actuator->SetIsNotInPreviewState(false);
399 };
400 longPressUpdate_ = longPressUpdate;
401 previewLongPressRecognizer_->SetOnAction(longPressUpdate);
402 previewLongPressRecognizer_->SetOnActionCancel(longPressCancel);
403 previewLongPressRecognizer_->SetGestureHub(gestureEventHub_);
404 auto eventHub = frameNode->GetEventHub<EventHub>();
405 CHECK_NULL_VOID(eventHub);
406 bool isAllowedDrag = gestureHub->IsAllowedDrag(eventHub);
407 if (!longPressRecognizer_->HasThumbnailCallback() && isAllowedDrag) {
408 auto callback = [weakPtr = gestureEventHub_](Offset point) {
409 auto gestureHub = weakPtr.Upgrade();
410 CHECK_NULL_VOID(gestureHub);
411 auto frameNode = gestureHub->GetFrameNode();
412 CHECK_NULL_VOID(frameNode);
413 auto pipeline = PipelineContext::GetCurrentContext();
414 CHECK_NULL_VOID(pipeline);
415 auto dragPreviewInfo = frameNode->GetDragPreview();
416 if (dragPreviewInfo.pixelMap != nullptr) {
417 gestureHub->SetPixelMap(dragPreviewInfo.pixelMap);
418 gestureHub->SetDragPreviewPixelMap(dragPreviewInfo.pixelMap);
419 } else if (dragPreviewInfo.customNode != nullptr) {
420 #if defined(PIXEL_MAP_SUPPORTED)
421 auto callback = [id = Container::CurrentId(), pipeline, gestureHub]
422 (std::shared_ptr<Media::PixelMap> pixelMap, int32_t arg, std::function<void()>) {
423 ContainerScope scope(id);
424 if (pixelMap != nullptr) {
425 auto customPixelMap = PixelMap::CreatePixelMap(reinterpret_cast<void*>(&pixelMap));
426 auto taskScheduler = pipeline->GetTaskExecutor();
427 CHECK_NULL_VOID(taskScheduler);
428 taskScheduler->PostTask([gestureHub, customPixelMap]() {
429 CHECK_NULL_VOID(gestureHub);
430 gestureHub->SetPixelMap(customPixelMap);
431 gestureHub->SetDragPreviewPixelMap(customPixelMap);
432 }, TaskExecutor::TaskType::UI);
433 }
434 };
435
436 OHOS::Ace::NG::ComponentSnapshot::Create(
437 dragPreviewInfo.customNode, std::move(callback), false, CREATE_PIXELMAP_TIME);
438 #endif
439 } else {
440 auto context = frameNode->GetRenderContext();
441 CHECK_NULL_VOID(context);
442 auto pixelMap = context->GetThumbnailPixelMap(true);
443 gestureHub->SetPixelMap(pixelMap);
444 }
445 };
446
447 longPressRecognizer_->SetThumbnailCallback(std::move(callback));
448 }
449 std::vector<RefPtr<NGGestureRecognizer>> recognizers { longPressRecognizer_, panRecognizer_ };
450 SequencedRecognizer_ = AceType::MakeRefPtr<SequencedRecognizer>(recognizers);
451 SequencedRecognizer_->RemainChildOnResetStatus();
452 previewLongPressRecognizer_->SetCoordinateOffset(Offset(coordinateOffset.GetX(), coordinateOffset.GetY()));
453 longPressRecognizer_->SetCoordinateOffset(Offset(coordinateOffset.GetX(), coordinateOffset.GetY()));
454 SequencedRecognizer_->SetCoordinateOffset(Offset(coordinateOffset.GetX(), coordinateOffset.GetY()));
455 SequencedRecognizer_->SetGetEventTargetImpl(getEventTargetImpl);
456 result.emplace_back(SequencedRecognizer_);
457 result.emplace_back(previewLongPressRecognizer_);
458 }
459
SetFilter(const RefPtr<DragEventActuator> & actuator)460 void DragEventActuator::SetFilter(const RefPtr<DragEventActuator>& actuator)
461 {
462 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent start setFilter.");
463 auto gestureHub = actuator->gestureEventHub_.Upgrade();
464 CHECK_NULL_VOID(gestureHub);
465 auto frameNode = gestureHub->GetFrameNode();
466 CHECK_NULL_VOID(frameNode);
467 auto parent = frameNode->GetParent();
468 CHECK_NULL_VOID(parent);
469 while (parent && parent->GetDepth() != 1) {
470 parent = parent->GetParent();
471 }
472 if (!parent) {
473 TAG_LOGD(AceLogTag::ACE_DRAG, "DragFrameNode is %{public}s, depth %{public}d, can not find filter root",
474 frameNode->GetTag().c_str(), frameNode->GetDepth());
475 return;
476 }
477 auto pipelineContext = PipelineContext::GetCurrentContext();
478 CHECK_NULL_VOID(pipelineContext);
479 auto manager = pipelineContext->GetOverlayManager();
480 CHECK_NULL_VOID(manager);
481 if (!manager->GetHasFilter() && !manager->GetIsOnAnimation()) {
482 if (frameNode->GetTag() == V2::WEB_ETS_TAG) {
483 #ifdef WEB_SUPPORTED
484 auto webPattern = frameNode->GetPattern<WebPattern>();
485 CHECK_NULL_VOID(webPattern);
486 bool isWebmageDrag = webPattern->IsImageDrag();
487 CHECK_NULL_VOID(isWebmageDrag && SystemProperties::GetDeviceType() == DeviceType::PHONE);
488 #endif
489 } else {
490 bool isBindOverlayValue = frameNode->GetLayoutProperty()->GetIsBindOverlayValue(false);
491 CHECK_NULL_VOID(isBindOverlayValue && SystemProperties::GetDeviceType() == DeviceType::PHONE);
492 }
493 // insert columnNode to rootNode
494 auto columnNode = FrameNode::CreateFrameNode(V2::COLUMN_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
495 AceType::MakeRefPtr<LinearLayoutPattern>(true));
496 columnNode->GetLayoutProperty()->UpdateMeasureType(MeasureType::MATCH_PARENT);
497 // set filter
498 TAG_LOGI(AceLogTag::ACE_DRAG, "User Device use default Filter");
499 auto container = Container::Current();
500 if (container && container->IsScenceBoardWindow()) {
501 auto windowScene = manager->FindWindowScene(frameNode);
502 manager->MountFilterToWindowScene(columnNode, windowScene);
503 } else {
504 columnNode->MountToParent(parent);
505 columnNode->OnMountToParentDone();
506 manager->SetHasFilter(true);
507 manager->SetFilterColumnNode(columnNode);
508 parent->MarkDirtyNode(NG::PROPERTY_UPDATE_BY_CHILD_REQUEST);
509 }
510 AnimationOption option;
511 BlurStyleOption styleOption;
512 styleOption.blurStyle = static_cast<BlurStyle>(BlurStyle::BACKGROUND_THIN);
513 styleOption.colorMode = static_cast<ThemeColorMode>(static_cast<int32_t>(ThemeColorMode::SYSTEM));
514 option.SetDuration(FILTER_TIMES);
515 option.SetCurve(Curves::SHARP);
516 columnNode->GetRenderContext()->UpdateBackBlurRadius(FILTER_VALUE);
517 AnimationUtils::Animate(
518 option, [columnNode, styleOption]() { columnNode->GetRenderContext()->UpdateBackBlurStyle(styleOption); },
519 option.GetOnFinishEvent());
520 }
521 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent set filter success.");
522 }
523
GetFloatImageOffset(const RefPtr<FrameNode> & frameNode,const RefPtr<PixelMap> & pixelMap)524 OffsetF DragEventActuator::GetFloatImageOffset(const RefPtr<FrameNode>& frameNode, const RefPtr<PixelMap>& pixelMap)
525 {
526 CHECK_NULL_RETURN(frameNode, OffsetF());
527 auto centerPosition = frameNode->GetPaintRectCenter();
528 float width = 0.0f;
529 float height = 0.0f;
530 if (pixelMap) {
531 width = pixelMap->GetWidth();
532 height = pixelMap->GetHeight();
533 }
534 auto offsetX = centerPosition.GetX() - width / 2.0f;
535 auto offsetY = centerPosition.GetY() - height / 2.0f;
536 #ifdef WEB_SUPPORTED
537 if (frameNode->GetTag() == V2::WEB_ETS_TAG) {
538 auto webPattern = frameNode->GetPattern<WebPattern>();
539 if (webPattern) {
540 auto offsetToWindow = frameNode->GetPaintRectOffset();
541 offsetX = offsetToWindow.GetX() + webPattern->GetDragOffset().GetX();
542 offsetY = offsetToWindow.GetY() + webPattern->GetDragOffset().GetY();
543 }
544 }
545 #endif
546 // Check web tag.
547 auto pipelineContext = PipelineContext::GetCurrentContext();
548 CHECK_NULL_RETURN(pipelineContext, OffsetF());
549 if (pipelineContext->HasFloatTitle()) {
550 offsetX -= static_cast<float>((CONTAINER_BORDER_WIDTH + CONTENT_PADDING).ConvertToPx());
551 offsetY -= static_cast<float>((CONTAINER_TITLE_HEIGHT + CONTAINER_BORDER_WIDTH).ConvertToPx());
552 }
553 return OffsetF(offsetX, offsetY);
554 }
555
UpdatePreviewPositionAndScale(const RefPtr<FrameNode> & imageNode,const OffsetF & frameOffset)556 void DragEventActuator::UpdatePreviewPositionAndScale(const RefPtr<FrameNode>& imageNode, const OffsetF& frameOffset)
557 {
558 auto imageContext = imageNode->GetRenderContext();
559 CHECK_NULL_VOID(imageContext);
560 imageContext->UpdatePosition(OffsetT<Dimension>(Dimension(frameOffset.GetX()), Dimension(frameOffset.GetY())));
561 ClickEffectInfo clickEffectInfo;
562 clickEffectInfo.level = ClickEffectLevel::LIGHT;
563 clickEffectInfo.scaleNumber = SCALE_NUMBER;
564 imageContext->UpdateClickEffectLevel(clickEffectInfo);
565 }
566
CreatePreviewNode(const RefPtr<FrameNode> & frameNode,OHOS::Ace::RefPtr<FrameNode> & imageNode)567 void DragEventActuator::CreatePreviewNode(const RefPtr<FrameNode>& frameNode, OHOS::Ace::RefPtr<FrameNode>& imageNode)
568 {
569 CHECK_NULL_VOID(frameNode);
570 auto pixelMap = frameNode->GetPixelMap();
571 CHECK_NULL_VOID(pixelMap);
572 auto frameOffset = frameNode->GetOffsetInScreen();
573 imageNode = FrameNode::GetOrCreateFrameNode(V2::IMAGE_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
574 []() {return AceType::MakeRefPtr<ImagePattern>(); });
575 CHECK_NULL_VOID(imageNode);
576 imageNode->SetDragPreviewOptions(frameNode->GetDragPreviewOption());
577
578 auto renderProps = imageNode->GetPaintProperty<ImageRenderProperty>();
579 renderProps->UpdateImageInterpolation(ImageInterpolation::HIGH);
580 auto props = imageNode->GetLayoutProperty<ImageLayoutProperty>();
581 props->UpdateAutoResize(false);
582 props->UpdateImageSourceInfo(ImageSourceInfo(pixelMap));
583 auto targetSize = CalcSize(NG::CalcLength(pixelMap->GetWidth()), NG::CalcLength(pixelMap->GetHeight()));
584 props->UpdateUserDefinedIdealSize(targetSize);
585
586 UpdatePreviewPositionAndScale(imageNode, frameOffset);
587 imageNode->MarkDirtyNode(NG::PROPERTY_UPDATE_MEASURE);
588 imageNode->MarkModifyDone();
589 imageNode->SetLayoutDirtyMarked(true);
590 imageNode->SetActive(true);
591 imageNode->CreateLayoutTask();
592 FlushSyncGeometryNodeTasks();
593 }
594
SetPreviewDefaultAnimateProperty(const RefPtr<FrameNode> & imageNode)595 void DragEventActuator::SetPreviewDefaultAnimateProperty(const RefPtr<FrameNode>& imageNode)
596 {
597 if (imageNode->IsPreviewNeedScale()) {
598 auto imageContext = imageNode->GetRenderContext();
599 CHECK_NULL_VOID(imageContext);
600 imageContext->UpdateTransformScale({ 1.0f, 1.0f });
601 imageContext->UpdateTransformTranslate({ 0.0f, 0.0f, 0.0f });
602 }
603 }
604
MountPixelMap(const RefPtr<OverlayManager> & manager,const RefPtr<GestureEventHub> & gestureHub,const RefPtr<FrameNode> & imageNode)605 void DragEventActuator::MountPixelMap(const RefPtr<OverlayManager>& manager, const RefPtr<GestureEventHub>& gestureHub,
606 const RefPtr<FrameNode>& imageNode)
607 {
608 CHECK_NULL_VOID(manager);
609 CHECK_NULL_VOID(imageNode);
610 CHECK_NULL_VOID(gestureHub);
611 auto columnNode = FrameNode::CreateFrameNode(V2::COLUMN_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
612 AceType::MakeRefPtr<LinearLayoutPattern>(true));
613 columnNode->AddChild(imageNode);
614 auto hub = columnNode->GetOrCreateGestureEventHub();
615 CHECK_NULL_VOID(hub);
616 hub->SetPixelMap(gestureHub->GetPixelMap());
617 auto container = Container::Current();
618 if (container && container->IsScenceBoardWindow()) {
619 auto frameNode = gestureHub->GetFrameNode();
620 CHECK_NULL_VOID(frameNode);
621 auto windowScene = manager->FindWindowScene(frameNode);
622 manager->MountPixelMapToWindowScene(columnNode, windowScene);
623 } else {
624 manager->MountPixelMapToRootNode(columnNode);
625 }
626 SetPreviewDefaultAnimateProperty(imageNode);
627 columnNode->MarkDirtyNode(NG::PROPERTY_UPDATE_MEASURE);
628 columnNode->MarkModifyDone();
629 columnNode->SetActive(true);
630 columnNode->CreateLayoutTask();
631 FlushSyncGeometryNodeTasks();
632 }
633
SetPixelMap(const RefPtr<DragEventActuator> & actuator)634 void DragEventActuator::SetPixelMap(const RefPtr<DragEventActuator>& actuator)
635 {
636 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent start set pixelMap");
637 auto pipelineContext = PipelineContext::GetCurrentContext();
638 CHECK_NULL_VOID(pipelineContext);
639 auto manager = pipelineContext->GetOverlayManager();
640 CHECK_NULL_VOID(manager);
641 if (manager->GetHasPixelMap()) {
642 TAG_LOGI(AceLogTag::ACE_DRAG, "Dragging animation is currently executing, unable to float other pixelMap.");
643 return;
644 }
645 auto gestureHub = actuator->gestureEventHub_.Upgrade();
646 CHECK_NULL_VOID(gestureHub);
647 auto frameNode = gestureHub->GetFrameNode();
648 CHECK_NULL_VOID(frameNode);
649 RefPtr<PixelMap> pixelMap = gestureHub->GetPixelMap();
650 CHECK_NULL_VOID(pixelMap);
651 auto width = pixelMap->GetWidth();
652 auto height = pixelMap->GetHeight();
653 auto offset = GetFloatImageOffset(frameNode, pixelMap);
654 // create imageNode
655 auto imageNode = FrameNode::GetOrCreateFrameNode(V2::IMAGE_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
656 []() { return AceType::MakeRefPtr<ImagePattern>(); });
657 imageNode->SetDragPreviewOptions(frameNode->GetDragPreviewOption());
658 auto renderProps = imageNode->GetPaintProperty<ImageRenderProperty>();
659 renderProps->UpdateImageInterpolation(ImageInterpolation::HIGH);
660 auto props = imageNode->GetLayoutProperty<ImageLayoutProperty>();
661 props->UpdateAutoResize(false);
662 props->UpdateImageSourceInfo(ImageSourceInfo(pixelMap));
663 auto targetSize = CalcSize(NG::CalcLength(width), NG::CalcLength(height));
664 props->UpdateUserDefinedIdealSize(targetSize);
665 auto imageContext = imageNode->GetRenderContext();
666 CHECK_NULL_VOID(imageContext);
667 imageContext->UpdatePosition(OffsetT<Dimension>(Dimension(offset.GetX()), Dimension(offset.GetY())));
668 ClickEffectInfo clickEffectInfo;
669 clickEffectInfo.level = ClickEffectLevel::LIGHT;
670 clickEffectInfo.scaleNumber = SCALE_NUMBER;
671 imageContext->UpdateClickEffectLevel(clickEffectInfo);
672 // create columnNode
673 auto columnNode = FrameNode::CreateFrameNode(V2::COLUMN_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
674 AceType::MakeRefPtr<LinearLayoutPattern>(true));
675 columnNode->AddChild(imageNode);
676 auto hub = columnNode->GetOrCreateGestureEventHub();
677 CHECK_NULL_VOID(hub);
678 hub->SetPixelMap(gestureHub->GetPixelMap());
679 // mount to rootNode
680 auto container = Container::Current();
681 if (container && container->IsScenceBoardWindow()) {
682 auto windowScene = manager->FindWindowScene(frameNode);
683 manager->MountPixelMapToWindowScene(columnNode, windowScene);
684 } else {
685 manager->MountPixelMapToRootNode(columnNode);
686 }
687 imageNode->MarkModifyDone();
688 imageNode->SetLayoutDirtyMarked(true);
689 imageNode->SetActive(true);
690 imageNode->CreateLayoutTask();
691 FlushSyncGeometryNodeTasks();
692 auto focusHub = frameNode->GetFocusHub();
693 CHECK_NULL_VOID(focusHub);
694 bool hasContextMenu = focusHub->FindContextMenuOnKeyEvent(OnKeyEventType::CONTEXT_MENU);
695 ShowPixelMapAnimation(imageNode, hasContextMenu);
696 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent set pixelMap success.");
697 SetPreviewDefaultAnimateProperty(imageNode);
698 }
699
SetEventColumn(const RefPtr<DragEventActuator> & actuator)700 void DragEventActuator::SetEventColumn(const RefPtr<DragEventActuator>& actuator)
701 {
702 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent start set eventColumn.");
703 auto pipelineContext = PipelineContext::GetCurrentContext();
704 CHECK_NULL_VOID(pipelineContext);
705 auto manager = pipelineContext->GetOverlayManager();
706 CHECK_NULL_VOID(manager);
707 if (manager->GetHasEvent()) {
708 return;
709 }
710 auto rootNode = pipelineContext->GetRootElement();
711 CHECK_NULL_VOID(rootNode);
712 auto geometryNode = rootNode->GetGeometryNode();
713 CHECK_NULL_VOID(geometryNode);
714 auto width = geometryNode->GetFrameSize().Width();
715 auto height = geometryNode->GetFrameSize().Height();
716 // create columnNode
717 auto columnNode = FrameNode::CreateFrameNode(V2::COLUMN_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
718 AceType::MakeRefPtr<LinearLayoutPattern>(true));
719 auto props = columnNode->GetLayoutProperty<LinearLayoutProperty>();
720 auto targetSize = CalcSize(NG::CalcLength(width), NG::CalcLength(height));
721 props->UpdateUserDefinedIdealSize(targetSize);
722 BindClickEvent(columnNode);
723 columnNode->MarkModifyDone();
724 auto container = Container::Current();
725 if (container && container->IsScenceBoardWindow()) {
726 auto gestureHub = actuator->gestureEventHub_.Upgrade();
727 CHECK_NULL_VOID(gestureHub);
728 auto frameNode = gestureHub->GetFrameNode();
729 CHECK_NULL_VOID(frameNode);
730 auto windowScene = manager->FindWindowScene(frameNode);
731 manager->MountEventToWindowScene(columnNode, windowScene);
732 } else {
733 manager->MountEventToRootNode(columnNode);
734 }
735 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent set eventColumn success.");
736 }
737
HideFilter()738 void DragEventActuator::HideFilter()
739 {
740 auto pipelineContext = PipelineContext::GetCurrentContext();
741 CHECK_NULL_VOID(pipelineContext);
742 auto manager = pipelineContext->GetOverlayManager();
743 CHECK_NULL_VOID(manager);
744 manager->RemoveFilterAnimation();
745 }
746
HidePixelMap(bool startDrag,double x,double y)747 void DragEventActuator::HidePixelMap(bool startDrag, double x, double y)
748 {
749 auto pipelineContext = PipelineContext::GetCurrentContext();
750 CHECK_NULL_VOID(pipelineContext);
751 auto manager = pipelineContext->GetOverlayManager();
752 CHECK_NULL_VOID(manager);
753 manager->RemovePixelMapAnimation(startDrag, x, y);
754 }
755
HideEventColumn()756 void DragEventActuator::HideEventColumn()
757 {
758 auto pipelineContext = PipelineContext::GetCurrentContext();
759 CHECK_NULL_VOID(pipelineContext);
760 auto manager = pipelineContext->GetOverlayManager();
761 CHECK_NULL_VOID(manager);
762 manager->RemoveEventColumn();
763 }
764
BindClickEvent(const RefPtr<FrameNode> & columnNode)765 void DragEventActuator::BindClickEvent(const RefPtr<FrameNode>& columnNode)
766 {
767 auto callback = [this, weak = WeakClaim(this)](GestureEvent& /* info */) {
768 HideEventColumn();
769 HidePixelMap();
770 HideFilter();
771 };
772 auto columnGestureHub = columnNode->GetOrCreateGestureEventHub();
773 CHECK_NULL_VOID(columnGestureHub);
774 auto clickListener = MakeRefPtr<ClickEvent>(std::move(callback));
775 columnGestureHub->AddClickEvent(clickListener);
776 if (!GetIsBindOverlayValue(Claim(this))) {
777 columnGestureHub->SetHitTestMode(HitTestMode::HTMBLOCK);
778 }
779 }
780
ShowPixelMapAnimation(const RefPtr<FrameNode> & imageNode,bool hasContextMenu)781 void DragEventActuator::ShowPixelMapAnimation(const RefPtr<FrameNode>& imageNode, bool hasContextMenu)
782 {
783 auto imageContext = imageNode->GetRenderContext();
784 CHECK_NULL_VOID(imageContext);
785 // pixel map animation
786 AnimationOption option;
787 option.SetDuration(PIXELMAP_ANIMATION_DURATION);
788 option.SetCurve(Curves::SHARP);
789 imageContext->UpdateTransformScale({ 1, 1 });
790 auto shadow = imageContext->GetBackShadow();
791 if (!shadow.has_value()) {
792 shadow = Shadow::CreateShadow(ShadowStyle::None);
793 }
794 imageContext->UpdateBackShadow(shadow.value());
795
796 AnimationUtils::Animate(
797 option,
798 [imageContext, shadow, hasContextMenu]() mutable {
799 auto color = shadow->GetColor();
800 auto newColor = Color::FromARGB(100, color.GetRed(), color.GetGreen(), color.GetBlue());
801 shadow->SetColor(newColor);
802 imageContext->UpdateBackShadow(shadow.value());
803 imageContext->UpdateTransformScale({ PIXELMAP_ANIMATION_SCALE, PIXELMAP_ANIMATION_SCALE });
804 if (hasContextMenu) {
805 BorderRadiusProperty borderRadius;
806 borderRadius.SetRadius(PIXELMAP_BORDER_RADIUS);
807 imageContext->UpdateBorderRadius(borderRadius);
808 }
809 },
810 option.GetOnFinishEvent());
811 }
812
SetThumbnailCallback(std::function<void (Offset)> && callback)813 void DragEventActuator::SetThumbnailCallback(std::function<void(Offset)>&& callback)
814 {
815 textDragCallback_ = callback;
816 longPressRecognizer_->SetThumbnailCallback(std::move(callback));
817 }
818
SetTextPixelMap(const RefPtr<GestureEventHub> & gestureHub)819 void DragEventActuator::SetTextPixelMap(const RefPtr<GestureEventHub>& gestureHub)
820 {
821 auto frameNode = gestureHub->GetFrameNode();
822 CHECK_NULL_VOID(frameNode);
823 auto pattern = frameNode->GetPattern<TextDragBase>();
824 CHECK_NULL_VOID(pattern);
825
826 auto dragNode = pattern->MoveDragNode();
827 pattern->CloseSelectOverlay();
828 CHECK_NULL_VOID(dragNode);
829 auto pixelMap = dragNode->GetRenderContext()->GetThumbnailPixelMap();
830 if (pixelMap) {
831 gestureHub->SetPixelMap(pixelMap);
832 } else {
833 gestureHub->SetPixelMap(nullptr);
834 }
835 }
836
SetTextAnimation(const RefPtr<GestureEventHub> & gestureHub,const Offset & globalLocation)837 void DragEventActuator::SetTextAnimation(const RefPtr<GestureEventHub>& gestureHub, const Offset& globalLocation)
838 {
839 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent start set textAnimation.");
840 auto pipelineContext = PipelineContext::GetCurrentContext();
841 CHECK_NULL_VOID(pipelineContext);
842 auto manager = pipelineContext->GetOverlayManager();
843 CHECK_NULL_VOID(manager);
844 manager->SetHasFilter(false);
845 CHECK_NULL_VOID(gestureHub);
846 auto frameNode = gestureHub->GetFrameNode();
847 CHECK_NULL_VOID(frameNode);
848 auto pattern = frameNode->GetPattern<TextDragBase>();
849 auto textBase = frameNode->GetPattern<TextBase>();
850 CHECK_NULL_VOID(pattern);
851 CHECK_NULL_VOID(textBase);
852 if (!textBase->BetweenSelectedPosition(globalLocation)) {
853 TAG_LOGD(AceLogTag::ACE_DRAG, "Position is between selected position, stop set text animation.");
854 return;
855 }
856 pattern->CloseHandleAndSelect();
857 auto dragNode = pattern->MoveDragNode();
858 CHECK_NULL_VOID(dragNode);
859 dragNode->SetDragPreviewOptions(frameNode->GetDragPreviewOption());
860 // create columnNode
861 auto columnNode = FrameNode::CreateFrameNode(V2::COLUMN_ETS_TAG, ElementRegister::GetInstance()->MakeUniqueId(),
862 AceType::MakeRefPtr<LinearLayoutPattern>(true));
863 columnNode->AddChild(dragNode);
864 // mount to rootNode
865 manager->MountPixelMapToRootNode(columnNode);
866 auto modifier = dragNode->GetPattern<TextDragPattern>()->GetOverlayModifier();
867 modifier->StartAnimate();
868 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent set text animation success.");
869 }
870
HideTextAnimation(bool startDrag,double globalX,double globalY)871 void DragEventActuator::HideTextAnimation(bool startDrag, double globalX, double globalY)
872 {
873 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent start hide text animation.");
874 auto gestureHub = gestureEventHub_.Upgrade();
875 CHECK_NULL_VOID(gestureHub);
876 bool isAllowedDrag = IsAllowedDrag();
877 if (!gestureHub->GetTextDraggable() || !isAllowedDrag) {
878 TAG_LOGD(AceLogTag::ACE_DRAG, "Text is not draggable, stop set hide text animation.");
879 return;
880 }
881 auto frameNode = gestureHub->GetFrameNode();
882 CHECK_NULL_VOID(frameNode);
883 auto pattern = frameNode->GetPattern<TextDragBase>();
884 CHECK_NULL_VOID(pattern);
885 auto removeColumnNode = [id = Container::CurrentId(), startDrag, weakPattern = WeakPtr<TextDragBase>(pattern),
886 weakEvent = gestureEventHub_] {
887 ContainerScope scope(id);
888 auto pipeline = PipelineContext::GetCurrentContext();
889 CHECK_NULL_VOID(pipeline);
890 auto manager = pipeline->GetOverlayManager();
891 CHECK_NULL_VOID(manager);
892 manager->RemovePixelMap();
893 if (!startDrag) {
894 auto pattern = weakPattern.Upgrade();
895 CHECK_NULL_VOID(pattern);
896 pattern->CreateHandles();
897 }
898 TAG_LOGD(AceLogTag::ACE_DRAG, "In removeColumnNode callback, set DragWindowVisible true.");
899 auto gestureHub = weakEvent.Upgrade();
900 CHECK_NULL_VOID(gestureHub);
901 if (!gestureHub->IsPixelMapNeedScale()) {
902 InteractionInterface::GetInstance()->SetDragWindowVisible(true);
903 }
904 gestureHub->SetPixelMap(nullptr);
905 };
906 AnimationOption option;
907 option.SetDuration(PIXELMAP_ANIMATION_DURATION);
908 option.SetCurve(Curves::SHARP);
909 option.SetOnFinishEvent(removeColumnNode);
910
911 auto pipeline = PipelineContext::GetCurrentContext();
912 CHECK_NULL_VOID(pipeline);
913 auto manager = pipeline->GetOverlayManager();
914 auto dragNode = manager->GetPixelMapNode();
915 CHECK_NULL_VOID(dragNode);
916 auto dragFrame = dragNode->GetGeometryNode()->GetFrameRect();
917 auto frameWidth = dragFrame.Width();
918 auto frameHeight = dragFrame.Height();
919 auto pixelMap = gestureHub->GetPixelMap();
920 float scale = 1.0f;
921 if (pixelMap) {
922 scale = gestureHub->GetPixelMapScale(pixelMap->GetHeight(), pixelMap->GetWidth());
923 }
924 auto context = dragNode->GetRenderContext();
925 CHECK_NULL_VOID(context);
926 context->UpdateTransformScale(VectorF(1.0f, 1.0f));
927 AnimationUtils::Animate(
928 option,
929 [context, startDrag, globalX, globalY, frameWidth, frameHeight, scale]() {
930 if (startDrag) {
931 context->UpdatePosition(OffsetT<Dimension>(Dimension(globalX + frameWidth * PIXELMAP_WIDTH_RATE),
932 Dimension(globalY + frameHeight * PIXELMAP_HEIGHT_RATE)));
933 context->UpdateTransformScale(VectorF(scale, scale));
934 context->OnModifyDone();
935 }
936 },
937 option.GetOnFinishEvent());
938 TAG_LOGD(AceLogTag::ACE_DRAG, "DragEvent set hide text animation success.");
939 }
GetIsBindOverlayValue(const RefPtr<DragEventActuator> & actuator)940 bool DragEventActuator::GetIsBindOverlayValue(const RefPtr<DragEventActuator>& actuator)
941 {
942 auto gestureHub = actuator->gestureEventHub_.Upgrade();
943 CHECK_NULL_RETURN(gestureHub, true);
944 auto frameNode = gestureHub->GetFrameNode();
945 CHECK_NULL_RETURN(frameNode, true);
946 bool isBindOverlayValue = frameNode->GetLayoutProperty()->GetIsBindOverlayValue(false);
947 return isBindOverlayValue;
948 }
949
IsAllowedDrag()950 bool DragEventActuator::IsAllowedDrag()
951 {
952 auto gestureHub = gestureEventHub_.Upgrade();
953 CHECK_NULL_RETURN(gestureHub, false);
954 auto frameNode = gestureHub->GetFrameNode();
955 CHECK_NULL_RETURN(frameNode, false);
956 auto eventHub = frameNode->GetEventHub<EventHub>();
957 CHECK_NULL_RETURN(eventHub, false);
958 bool isAllowedDrag = gestureHub->IsAllowedDrag(eventHub);
959 return isAllowedDrag;
960 }
961
CopyDragEvent(const RefPtr<DragEventActuator> & dragEventActuator)962 void DragEventActuator::CopyDragEvent(const RefPtr<DragEventActuator>& dragEventActuator)
963 {
964 userCallback_ = dragEventActuator->userCallback_;
965 customCallback_ = dragEventActuator->customCallback_;
966 panRecognizer_ = MakeRefPtr<PanRecognizer>(fingers_, direction_, distance_);
967 panRecognizer_->SetGestureInfo(MakeRefPtr<GestureInfo>(GestureTypeName::DRAG, true));
968 longPressRecognizer_ = AceType::MakeRefPtr<LongPressRecognizer>(LONG_PRESS_DURATION, fingers_, false, false);
969 longPressRecognizer_->SetGestureInfo(MakeRefPtr<GestureInfo>(GestureTypeName::DRAG, true));
970 previewLongPressRecognizer_ =
971 AceType::MakeRefPtr<LongPressRecognizer>(PREVIEW_LONG_PRESS_RECONGNIZER, fingers_, false, false);
972 previewLongPressRecognizer_->SetGestureInfo(MakeRefPtr<GestureInfo>(GestureTypeName::DRAG, true));
973 isNotInPreviewState_ = false;
974 actionStart_ = dragEventActuator->actionStart_;
975 longPressUpdate_ = dragEventActuator->longPressUpdate_;
976 actionCancel_ = dragEventActuator->actionCancel_;
977 textDragCallback_ = dragEventActuator->textDragCallback_;
978 longPressInfo_ = dragEventActuator->longPressInfo_;
979 }
980
FlushSyncGeometryNodeTasks()981 void DragEventActuator::FlushSyncGeometryNodeTasks()
982 {
983 auto pipeline = PipelineBase::GetCurrentContext();
984 CHECK_NULL_VOID(pipeline);
985 pipeline->FlushSyncGeometryNodeTasks();
986 }
987 } // namespace OHOS::Ace::NG
988