• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2023 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/common/event_manager.h"
17 
18 #include "base/geometry/ng/point_t.h"
19 #include "base/log/ace_trace.h"
20 #include "base/log/dump_log.h"
21 #include "base/memory/ace_type.h"
22 #include "base/thread/frame_trace_adapter.h"
23 #include "base/utils/utils.h"
24 #include "core/common/container.h"
25 #include "core/components_ng/base/frame_node.h"
26 #include "core/components_ng/event/touch_event.h"
27 #include "core/components_ng/gestures/recognizers/recognizer_group.h"
28 #include "core/components_ng/manager/select_overlay/select_overlay_manager.h"
29 #include "core/event/ace_events.h"
30 #include "core/event/key_event.h"
31 #include "core/event/touch_event.h"
32 #include "core/gestures/gesture_referee.h"
33 #include "core/pipeline/base/element.h"
34 #include "core/pipeline/base/render_node.h"
35 
36 namespace OHOS::Ace {
37 constexpr uint8_t KEYS_MAX_VALUE = 3;
38 constexpr int32_t DUMP_START_NUMBER = 4;
39 constexpr int32_t DUMP_LIMIT_SIZE = 500;
40 constexpr int64_t EVENT_CLEAR_DURATION = 1000;
41 constexpr int64_t TRANSLATE_NS_TO_MS = 1000000;
42 const std::string SHORT_CUT_VALUE_X = "X";
43 const std::string SHORT_CUT_VALUE_Y = "Y";
44 const std::string SHORT_CUT_VALUE_Z = "Z";
45 const std::string SHORT_CUT_VALUE_A = "A";
46 const std::string SHORT_CUT_VALUE_C = "C";
47 const std::string SHORT_CUT_VALUE_V = "V";
48 enum class CtrlKeysBit {
49     CTRL = 1,
50     SHIFT = 2,
51     ALT = 4,
52 };
53 
TouchTest(const TouchEvent & touchPoint,const RefPtr<RenderNode> & renderNode,TouchRestrict & touchRestrict,const Offset & offset,float viewScale,bool needAppend)54 void EventManager::TouchTest(const TouchEvent& touchPoint, const RefPtr<RenderNode>& renderNode,
55     TouchRestrict& touchRestrict, const Offset& offset, float viewScale, bool needAppend)
56 {
57     ContainerScope scope(instanceId_);
58 
59     ACE_FUNCTION_TRACE();
60     CHECK_NULL_VOID(renderNode);
61     // first clean.
62     referee_->CleanGestureScope(touchPoint.id);
63     // collect
64     TouchTestResult hitTestResult;
65     const Point point { touchPoint.x, touchPoint.y, touchPoint.sourceType };
66     // For root node, the parent local point is the same as global point.
67     renderNode->TouchTest(point, point, touchRestrict, hitTestResult);
68     if (needAppend) {
69 #ifdef OHOS_STANDARD_SYSTEM
70         for (auto entry = hitTestResult.begin(); entry != hitTestResult.end(); ++entry) {
71             if ((*entry)) {
72                 (*entry)->SetSubPipelineGlobalOffset(offset, viewScale);
73             }
74         }
75 #endif
76         TouchTestResult prevHitTestResult = touchTestResults_[touchPoint.id];
77         hitTestResult.splice(hitTestResult.end(), prevHitTestResult);
78     }
79     touchTestResults_[touchPoint.id] = std::move(hitTestResult);
80 }
81 
TouchTest(const TouchEvent & touchPoint,const RefPtr<NG::FrameNode> & frameNode,TouchRestrict & touchRestrict,const Offset & offset,float viewScale,bool needAppend)82 void EventManager::TouchTest(const TouchEvent& touchPoint, const RefPtr<NG::FrameNode>& frameNode,
83     TouchRestrict& touchRestrict, const Offset& offset, float viewScale, bool needAppend)
84 {
85     ContainerScope scope(instanceId_);
86 
87     ACE_FUNCTION_TRACE();
88     CHECK_NULL_VOID(frameNode);
89     // collect
90     TouchTestResult hitTestResult;
91     const NG::PointF point { touchPoint.x, touchPoint.y };
92     refereeNG_->CheckSourceTypeChange(touchPoint.sourceType);
93     if (refereeNG_->QueryAllDone(touchPoint.id)) {
94         refereeNG_->CleanGestureScope(touchPoint.id);
95         if (touchTestResults_.empty() && refereeNG_->QueryAllDone()) {
96             innerEventWin_ = false;
97             responseCtrl_->Reset();
98             refereeNG_->CleanAll();
99         }
100     }
101     if (downFingerIds_.empty() && refereeNG_->QueryAllDone()) {
102         refereeNG_->ForceCleanGestureReferee();
103         CleanGestureEventHub();
104     }
105     if (frameNode->HaveSecurityComponent()) {
106         std::vector<NG::RectF> rect;
107         frameNode->CheckSecurityComponentStatus(rect);
108     }
109     if (!needAppend && touchTestResults_.empty()) {
110         NG::NGGestureRecognizer::ResetGlobalTransCfg();
111     }
112     // For root node, the parent local point is the same as global point.
113     frameNode->TouchTest(point, point, point, touchRestrict, hitTestResult, touchPoint.id);
114     if (needAppend) {
115 #ifdef OHOS_STANDARD_SYSTEM
116         for (const auto& entry : hitTestResult) {
117             if (entry) {
118                 entry->SetSubPipelineGlobalOffset(offset, viewScale);
119             }
120         }
121 #endif
122         TouchTestResult prevHitTestResult = touchTestResults_[touchPoint.id];
123         hitTestResult.splice(hitTestResult.end(), prevHitTestResult);
124     }
125     std::list<RefPtr<NG::NGGestureRecognizer>> hitTestRecognizers;
126     for (const auto& item : hitTestResult) {
127         auto recognizer = AceType::DynamicCast<NG::NGGestureRecognizer>(item);
128         if (recognizer) {
129             hitTestRecognizers.emplace_back(recognizer);
130         }
131     }
132     SetHittedFrameNode(hitTestRecognizers);
133     touchTestResults_[touchPoint.id] = std::move(hitTestResult);
134     auto container = Container::Current();
135     CHECK_NULL_VOID(container);
136     std::map<int32_t, NG::TouchTestResultInfo> touchTestResultInfo;
137     for (const auto& item : touchTestResults_[touchPoint.id]) {
138         auto node = item->GetAttachedNode().Upgrade();
139         if (!node) {
140             continue;
141         }
142         auto frameNode = AceType::DynamicCast<NG::FrameNode>(node);
143         if (!frameNode) {
144             continue;
145         }
146         touchTestResultInfo[frameNode->GetId()] = { frameNode->GetId(), frameNode->GetTag(),
147             frameNode->GetInspectorIdValue(""), frameNode->GetGeometryNode()->GetFrameRect().ToString(),
148             frameNode->GetDepth() };
149     }
150     std::string resultInfo = std::string("fingerId: ").append(std::to_string(touchPoint.id));
151     for (const auto& item : touchTestResultInfo) {
152         resultInfo.append(" id: ")
153             .append(std::to_string(item.first))
154             .append(", tag: ")
155             .append(item.second.tag)
156             .append(", inspectorId: ")
157             .append(item.second.inspectorId)
158             .append(", frameRect: ")
159             .append(item.second.frameRect)
160             .append(", depth: ")
161             .append(std::to_string(item.second.depth))
162             .append(".");
163     }
164     TAG_LOGI(AceLogTag::ACE_INPUTTRACKING, "Touch test hitted node info: %{public}s", resultInfo.c_str());
165     if (touchTestResultInfo.empty()) {
166         TAG_LOGW(AceLogTag::ACE_INPUTTRACKING, "Touch test result is empty.");
167         std::list<std::pair<int32_t, std::string>> dumpList;
168         eventTree_.Dump(dumpList, 0, DUMP_START_NUMBER);
169         int32_t dumpCount = 0;
170         for (auto& item : dumpList) {
171             dumpCount++;
172             if (dumpCount > DUMP_LIMIT_SIZE) {
173                 TAG_LOGW(AceLogTag::ACE_INPUTTRACKING,
174                     "EventTreeDumpInfo size is over limit, the following info is dropped!");
175                 break;
176             }
177             TAG_LOGI(AceLogTag::ACE_INPUTTRACKING, "EventTreeDumpInfo: %{public}s", item.second.c_str());
178         }
179     }
180     LogTouchTestResultRecognizers(touchTestResults_[touchPoint.id]);
181 }
182 
LogTouchTestResultRecognizers(const TouchTestResult & result)183 void EventManager::LogTouchTestResultRecognizers(const TouchTestResult& result)
184 {
185     std::map<std::string, std::list<NG::TouchTestResultInfo>> hittedRecognizerInfo;
186     for (const auto& item : result) {
187         if (AceType::InstanceOf<NG::MultiFingersRecognizer>(item) && !AceType::InstanceOf<NG::RecognizerGroup>(item)) {
188             auto node = item->GetAttachedNode().Upgrade();
189             if (!node) {
190                 hittedRecognizerInfo.emplace(AceType::TypeName(item), std::list<NG::TouchTestResultInfo>());
191                 continue;
192             }
193             auto frameNode = AceType::DynamicCast<NG::FrameNode>(node);
194             if (!frameNode) {
195                 hittedRecognizerInfo.emplace(AceType::TypeName(item), std::list<NG::TouchTestResultInfo>());
196                 continue;
197             }
198             hittedRecognizerInfo[AceType::TypeName(item)].emplace_back(NG::TouchTestResultInfo {
199                 frameNode->GetId(), frameNode->GetTag(), frameNode->GetInspectorIdValue("") });
200         }
201         auto group = AceType::DynamicCast<NG::RecognizerGroup>(item);
202         if (group) {
203             group->AddHittedRecognizerType(hittedRecognizerInfo);
204         }
205     }
206     std::string hittedRecognizerTypeInfo = std::string("Touch test hitted recognizer type info: ");
207     for (const auto& item : hittedRecognizerInfo) {
208         hittedRecognizerTypeInfo.append("recognizer type ").append(item.first).append(" node info:");
209         for (const auto& nodeInfo : item.second) {
210             hittedRecognizerTypeInfo.append(" { id: ")
211                 .append(std::to_string(nodeInfo.nodeId))
212                 .append(", tag: ")
213                 .append(nodeInfo.tag)
214                 .append(", inspectorId: ")
215                 .append(nodeInfo.inspectorId)
216                 .append(" };");
217         }
218     }
219     TAG_LOGI(AceLogTag::ACE_INPUTTRACKING, "%{public}s", hittedRecognizerTypeInfo.c_str());
220 }
221 
PostEventTouchTest(const TouchEvent & touchPoint,const RefPtr<NG::UINode> & uiNode,TouchRestrict & touchRestrict)222 bool EventManager::PostEventTouchTest(
223     const TouchEvent& touchPoint, const RefPtr<NG::UINode>& uiNode, TouchRestrict& touchRestrict)
224 {
225     ContainerScope scope(instanceId_);
226     ACE_FUNCTION_TRACE();
227     CHECK_NULL_RETURN(uiNode, false);
228     // collect
229     TouchTestResult hitTestResult;
230     const NG::PointF point { touchPoint.x, touchPoint.y };
231     postEventRefereeNG_->CheckSourceTypeChange(touchPoint.sourceType);
232     if (postEventRefereeNG_->QueryAllDone(touchPoint.id)) {
233         postEventRefereeNG_->CleanGestureScope(touchPoint.id);
234         if (postEventTouchTestResults_.empty() && postEventRefereeNG_->QueryAllDone()) {
235             postEventRefereeNG_->CleanAll();
236         }
237     }
238     // For root node, the parent local point is the same as global point.
239     uiNode->TouchTest(point, point, point, touchRestrict, hitTestResult, touchPoint.id);
240     for (const auto& item : hitTestResult) {
241         item->SetIsPostEventResult(true);
242         auto group = AceType::DynamicCast<NG::RecognizerGroup>(item);
243         if (group) {
244             group->SetIsPostEventResultRecursively(true);
245         }
246     }
247     auto result = !hitTestResult.empty();
248     postEventTouchTestResults_[touchPoint.id] = std::move(hitTestResult);
249     return result;
250 }
251 
TouchTest(const AxisEvent & event,const RefPtr<NG::FrameNode> & frameNode,TouchRestrict & touchRestrict)252 void EventManager::TouchTest(
253     const AxisEvent& event, const RefPtr<NG::FrameNode>& frameNode, TouchRestrict& touchRestrict)
254 {
255     ContainerScope scope(instanceId_);
256 
257     if (refereeNG_->CheckSourceTypeChange(event.sourceType, true)) {
258         refereeNG_->CleanAll(true);
259     }
260     ACE_FUNCTION_TRACE();
261     CHECK_NULL_VOID(frameNode);
262     if (axisTouchTestResults_.empty() && refereeNG_->QueryAllDone()) {
263         responseCtrl_->Reset();
264     }
265     // collect
266     const NG::PointF point { event.x, event.y };
267     if (frameNode->HaveSecurityComponent()) {
268         std::vector<NG::RectF> rect;
269         frameNode->CheckSecurityComponentStatus(rect);
270     }
271     // For root node, the parent local point is the same as global point.
272     TouchTestResult hitTestResult;
273     frameNode->TouchTest(point, point, point, touchRestrict, hitTestResult, event.id);
274     axisTouchTestResults_[event.id] = std::move(hitTestResult);
275 }
276 
HasDifferentDirectionGesture()277 bool EventManager::HasDifferentDirectionGesture()
278 {
279     uint8_t verticalFlag = 0;
280     uint8_t horizontalFlag = 0;
281     for (const auto& axisResult : axisTouchTestResults_) {
282         auto axisRecognizerList = axisResult.second;
283         for (const auto& axisRecognizer : axisRecognizerList) {
284             if (!axisRecognizer) {
285                 continue;
286             }
287             auto axisDirection = axisRecognizer->GetAxisDirection();
288             if (axisDirection == Axis::FREE) {
289                 return true;
290             }
291             if (axisDirection == Axis::VERTICAL) {
292                 verticalFlag = 0x1;
293             } else if (axisDirection == Axis::HORIZONTAL) {
294                 horizontalFlag = 0x2;
295             }
296             if ((verticalFlag | horizontalFlag) == 0x3) {
297                 return true;
298             }
299         }
300     }
301     return (verticalFlag | horizontalFlag) == 0x3;
302 }
303 
HandleGlobalEvent(const TouchEvent & touchPoint,const RefPtr<TextOverlayManager> & textOverlayManager)304 void EventManager::HandleGlobalEvent(const TouchEvent& touchPoint, const RefPtr<TextOverlayManager>& textOverlayManager)
305 {
306     if (touchPoint.type != TouchType::DOWN) {
307         return;
308     }
309     auto coordinateOffset = textOverlayManager->GetCoordinateOffset();
310     const Point point { touchPoint.x - coordinateOffset.GetX(), touchPoint.y - coordinateOffset.GetY(),
311         touchPoint.sourceType };
312     CHECK_NULL_VOID(textOverlayManager);
313     auto textOverlayBase = textOverlayManager->GetTextOverlayBase();
314     CHECK_NULL_VOID(textOverlayBase);
315     auto targetNode = textOverlayManager->GetTargetNode();
316     CHECK_NULL_VOID(targetNode);
317     for (auto& rect : textOverlayManager->GetTextOverlayRect()) {
318         if (rect.IsInRegion(point)) {
319             inSelectedRect_ = true;
320         }
321     }
322     for (auto& rect : textOverlayBase->GetSelectedRect()) {
323         if (rect.IsInRegion(point)) {
324             inSelectedRect_ = true;
325         }
326     }
327     if (!inSelectedRect_) {
328         textOverlayManager->PopTextOverlay();
329         textOverlayBase->ChangeSelection(0, 0);
330         textOverlayBase->MarkIsOverlayShowed(false);
331         targetNode->MarkNeedRender();
332     }
333     inSelectedRect_ = false;
334 }
335 
HandleGlobalEventNG(const TouchEvent & touchPoint,const RefPtr<NG::SelectOverlayManager> & selectOverlayManager,const NG::OffsetF & rootOffset)336 void EventManager::HandleGlobalEventNG(const TouchEvent& touchPoint,
337     const RefPtr<NG::SelectOverlayManager>& selectOverlayManager, const NG::OffsetF& rootOffset)
338 {
339     CHECK_NULL_VOID(selectOverlayManager);
340     auto isMousePressAtSelectedNode = false;
341     if (touchPoint.type == TouchType::DOWN &&
342         (touchTestResults_.find(touchPoint.id) != touchTestResults_.end() || !currMouseTestResults_.empty())) {
343         int32_t selectedNodeId = -1;
344         if (touchPoint.sourceType == SourceType::MOUSE) {
345             selectOverlayManager->GetSelectedNodeIdByMouse(selectedNodeId);
346         }
347         if (!touchTestResults_.empty()) {
348             std::vector<std::string> touchTestIds;
349             GetTouchTestIds(touchPoint, touchTestIds, isMousePressAtSelectedNode, selectedNodeId);
350             selectOverlayManager->SetOnTouchTestResults(touchTestIds);
351         } else {
352             // When right-click on another component, close the current component selection.
353             CheckMouseTestResults(isMousePressAtSelectedNode, selectedNodeId);
354         }
355     }
356     selectOverlayManager->HandleGlobalEvent(touchPoint, rootOffset, isMousePressAtSelectedNode);
357 }
358 
CheckMouseTestResults(bool & isMousePressAtSelectedNode,int32_t selectedNodeId)359 void EventManager::CheckMouseTestResults(bool& isMousePressAtSelectedNode, int32_t selectedNodeId)
360 {
361     for (const auto& result : currMouseTestResults_) {
362         TAG_LOGD(AceLogTag::ACE_INPUTTRACKING,
363             "HandleGlobalEventNG selectedNodeId: %{public}d mouseTestResult id is: %{public}d", selectedNodeId,
364             result->GetNodeId());
365         if (result->GetNodeId() == selectedNodeId) {
366             isMousePressAtSelectedNode = true;
367         }
368     }
369 }
370 
GetTouchTestIds(const TouchEvent & touchPoint,std::vector<std::string> & touchTestIds,bool & isMousePressAtSelectedNode,int32_t selectedNodeId)371 void EventManager::GetTouchTestIds(const TouchEvent& touchPoint, std::vector<std::string>& touchTestIds,
372     bool& isMousePressAtSelectedNode, int32_t selectedNodeId)
373 {
374     const auto& resultList = touchTestResults_[touchPoint.id];
375     for (const auto& result : resultList) {
376         auto eventTarget = result->GetEventTarget();
377         if (eventTarget.has_value()) {
378             touchTestIds.emplace_back(eventTarget.value().id);
379             if (eventTarget.value().id == std::to_string(selectedNodeId)) {
380                 TAG_LOGD(AceLogTag::ACE_INPUTTRACKING,
381                     "HandleGlobalEventNG selectedNodeId: %{public}d eventTarget id is: %{public}s", selectedNodeId,
382                     eventTarget.value().id.c_str());
383                 isMousePressAtSelectedNode = true;
384             }
385         }
386     }
387 }
388 
HandleOutOfRectCallback(const Point & point,std::vector<RectCallback> & rectCallbackList)389 void EventManager::HandleOutOfRectCallback(const Point& point, std::vector<RectCallback>& rectCallbackList)
390 {
391     for (auto iter = rectCallbackList.begin(); iter != rectCallbackList.end();) {
392         auto rectCallback = *iter;
393         auto rectGetCallback = rectCallback.rectGetCallback;
394         if (!rectGetCallback) {
395             ++iter;
396             continue;
397         }
398         std::vector<Rect> rectList;
399         rectGetCallback(rectList);
400         if (std::any_of(
401                 rectList.begin(), rectList.end(), [point](const Rect& rect) { return rect.IsInRegion(point); })) {
402             ++iter;
403             continue;
404         }
405         for (const auto& rect : rectList) {
406             LOGI("Point(%{public}f, %{public}f) out of Rect-[%{public}f, %{public}f, %{public}f, %{public}f]",
407                 point.GetX(), point.GetY(), rect.Left(), rect.Right(), rect.Top(), rect.Bottom());
408         }
409         if (point.GetSourceType() == SourceType::TOUCH) {
410             if (!rectCallback.touchCallback) {
411                 ++iter;
412                 continue;
413             }
414             rectCallback.touchCallback();
415         } else if (point.GetSourceType() == SourceType::MOUSE) {
416             if (!rectCallback.mouseCallback) {
417                 ++iter;
418                 continue;
419             }
420             rectCallback.mouseCallback();
421         }
422         iter = rectCallbackList.erase(iter);
423     }
424 }
425 
TouchTest(const AxisEvent & event,const RefPtr<RenderNode> & renderNode,TouchRestrict & touchRestrict)426 void EventManager::TouchTest(
427     const AxisEvent& event, const RefPtr<RenderNode>& renderNode, TouchRestrict& touchRestrict)
428 {
429     ContainerScope scope(instanceId_);
430 
431     ACE_FUNCTION_TRACE();
432     CHECK_NULL_VOID(renderNode);
433     // collect
434     const Point point { event.x, event.y, event.sourceType };
435     // For root node, the parent local point is the same as global point.
436     TouchTestResult hitTestResult;
437     renderNode->TouchTest(point, point, touchRestrict, hitTestResult);
438     axisTouchTestResults_[event.id] = std::move(hitTestResult);
439 }
440 
FlushTouchEventsBegin(const std::list<TouchEvent> & touchEvents)441 void EventManager::FlushTouchEventsBegin(const std::list<TouchEvent>& touchEvents)
442 {
443     for (auto iter = touchEvents.begin(); iter != touchEvents.end(); ++iter) {
444         const auto result = touchTestResults_.find((*iter).id);
445         if (result != touchTestResults_.end()) {
446             for (auto entry = result->second.rbegin(); entry != result->second.rend(); ++entry) {
447                 (*entry)->OnFlushTouchEventsBegin();
448             }
449         }
450     }
451 }
452 
FlushTouchEventsEnd(const std::list<TouchEvent> & touchEvents)453 void EventManager::FlushTouchEventsEnd(const std::list<TouchEvent>& touchEvents)
454 {
455     for (auto iter = touchEvents.begin(); iter != touchEvents.end(); ++iter) {
456         const auto result = touchTestResults_.find((*iter).id);
457         if (result != touchTestResults_.end()) {
458             for (auto entry = result->second.rbegin(); entry != result->second.rend(); ++entry) {
459                 (*entry)->OnFlushTouchEventsEnd();
460             }
461         }
462     }
463 }
464 
PostEventFlushTouchEventEnd(const TouchEvent & touchEvent)465 void EventManager::PostEventFlushTouchEventEnd(const TouchEvent& touchEvent)
466 {
467     const auto result = postEventTouchTestResults_.find(touchEvent.id);
468     if (result != postEventTouchTestResults_.end()) {
469         for (auto entry = result->second.rbegin(); entry != result->second.rend(); ++entry) {
470             (*entry)->OnFlushTouchEventsEnd();
471         }
472     }
473 }
474 
CheckTouchEvent(TouchEvent touchEvent)475 void EventManager::CheckTouchEvent(TouchEvent touchEvent)
476 {
477     auto touchEventFindResult = downFingerIds_.find(touchEvent.id);
478     if (touchEvent.type == TouchType::DOWN) {
479         if (touchEventFindResult == downFingerIds_.end()) {
480             downFingerIds_.insert(touchEvent.id);
481         } else {
482             TAG_LOGW(AceLogTag::ACE_INPUTTRACKING, "EventManager receive DOWN event twice,"
483                 " touchEvent id is %{public}d", touchEvent.id);
484         }
485     } else if (touchEvent.type == TouchType::UP) {
486         if (touchEventFindResult == downFingerIds_.end()) {
487             TAG_LOGW(AceLogTag::ACE_INPUTTRACKING, "EventManager receive UP event without receive DOWN event,"
488                 " touchEvent id is %{public}d", touchEvent.id);
489         } else {
490             downFingerIds_.erase(touchEvent.id);
491         }
492     }
493 }
494 
DispatchTouchEvent(const TouchEvent & event)495 bool EventManager::DispatchTouchEvent(const TouchEvent& event)
496 {
497     CheckTouchEvent(event);
498     ContainerScope scope(instanceId_);
499     TouchEvent point = event;
500     if (point.type == TouchType::PULL_MOVE || point.pullType == TouchType::PULL_MOVE) {
501         isDragging_ = false;
502         point.type = TouchType::CANCEL;
503     }
504     if (point.type == TouchType::PULL_UP || point.type == TouchType::UP) {
505         isDragging_ = false;
506         point.type = TouchType::UP;
507     }
508     ACE_SCOPED_TRACE(
509         "DispatchTouchEvent id:%d, pointX=%f pointY=%f type=%d", point.id, point.x, point.y, (int)point.type);
510     const auto iter = touchTestResults_.find(point.id);
511     if (iter == touchTestResults_.end()) {
512         return false;
513     }
514 
515     if (point.type == TouchType::DOWN) {
516         refereeNG_->CleanGestureRefereeState(event.id);
517         int64_t currentEventTime = static_cast<int64_t>(point.time.time_since_epoch().count());
518         int64_t lastEventTime = static_cast<int64_t>(lastEventTime_.time_since_epoch().count());
519         int64_t duration = static_cast<int64_t>((currentEventTime - lastEventTime) / TRANSLATE_NS_TO_MS);
520         if (duration >= EVENT_CLEAR_DURATION && !refereeNG_->CheckGestureRefereeState()) {
521             TAG_LOGW(AceLogTag::ACE_INPUTTRACKING, "GestureReferee check state fail, force clean gestureReferee.");
522             std::list<std::pair<int32_t, std::string>> dumpList;
523             eventTree_.Dump(dumpList, 0);
524             for (auto& item : dumpList) {
525                 TAG_LOGI(AceLogTag::ACE_INPUTTRACKING, "EventTreeDumpInfo: %{public}s", item.second.c_str());
526             }
527             refereeNG_->ForceCleanGestureReferee();
528         }
529         // first collect gesture into gesture referee.
530         if (Container::IsCurrentUseNewPipeline()) {
531             refereeNG_->AddGestureToScope(point.id, iter->second);
532         }
533         // add gesture snapshot to dump
534         for (const auto& target : iter->second) {
535             AddGestureSnapshot(point.id, 0, target);
536         }
537     }
538 
539     bool dispatchSuccess = true;
540     for (auto entry = iter->second.rbegin(); entry != iter->second.rend(); ++entry) {
541         if (!(*entry)->DispatchMultiContainerEvent(point)) {
542             dispatchSuccess = false;
543             break;
544         }
545     }
546     // If one gesture recognizer has already been won, other gesture recognizers will still be affected by
547     // the event, each recognizer needs to filter the extra events by itself.
548     if (dispatchSuccess) {
549         if (Container::IsCurrentUseNewPipeline()) {
550             // Need update here: onTouch/Recognizer need update
551             bool isStopTouchEvent = false;
552             for (const auto& entry : iter->second) {
553                 auto recognizer = AceType::DynamicCast<NG::NGGestureRecognizer>(entry);
554                 if (recognizer) {
555                     entry->HandleMultiContainerEvent(point);
556                     eventTree_.AddGestureProcedure(reinterpret_cast<uintptr_t>(AceType::RawPtr(recognizer)), point,
557                         NG::TransRefereeState(recognizer->GetRefereeState()),
558                         NG::TransGestureDisposal(recognizer->GetGestureDisposal()));
559                 }
560                 if (!recognizer && !isStopTouchEvent) {
561                     isStopTouchEvent = !entry->HandleMultiContainerEvent(point);
562                     eventTree_.AddGestureProcedure(reinterpret_cast<uintptr_t>(AceType::RawPtr(entry)),
563                         std::string("Handle").append(GestureSnapshot::TransTouchType(point.type)), "", "");
564                 }
565             }
566         } else {
567             for (const auto& entry : iter->second) {
568                 if (!entry->HandleMultiContainerEvent(point)) {
569                     break;
570                 }
571             }
572         }
573     }
574 
575     if (point.type == TouchType::UP || point.type == TouchType::CANCEL) {
576         FrameTraceAdapter* ft = FrameTraceAdapter::GetInstance();
577         if (ft != nullptr) {
578             ft->SetFrameTraceLimit();
579         }
580         refereeNG_->CleanGestureScope(point.id);
581         referee_->CleanGestureScope(point.id);
582         touchTestResults_.erase(point.id);
583         if (touchTestResults_.empty()) {
584             refereeNG_->CleanRedundanceScope();
585         }
586     }
587 
588     lastEventTime_ = point.time;
589     return true;
590 }
591 
PostEventDispatchTouchEvent(const TouchEvent & event)592 bool EventManager::PostEventDispatchTouchEvent(const TouchEvent& event)
593 {
594     ContainerScope scope(instanceId_);
595     TouchEvent point = event;
596     const auto iter = postEventTouchTestResults_.find(point.id);
597     if (iter == postEventTouchTestResults_.end()) {
598         return false;
599     }
600     ACE_SCOPED_TRACE(
601         "PostEventDispatchTouchEvent id:%d, pointX=%f pointY=%f type=%d", point.id, point.x, point.y, (int)point.type);
602 
603     if (point.type == TouchType::DOWN) {
604         // first collect gesture into gesture referee.
605         postEventRefereeNG_->AddGestureToScope(point.id, iter->second);
606         // add gesture snapshot to dump
607         for (const auto& target : iter->second) {
608             AddGestureSnapshot(point.id, 0, target);
609         }
610     }
611 
612     bool dispatchSuccess = true;
613     for (auto entry = iter->second.rbegin(); entry != iter->second.rend(); ++entry) {
614         if (!(*entry)->DispatchMultiContainerEvent(point)) {
615             dispatchSuccess = false;
616             break;
617         }
618     }
619     // If one gesture recognizer has already been won, other gesture recognizers will still be affected by
620     // the event, each recognizer needs to filter the extra events by itself.
621     if (dispatchSuccess) {
622         bool isStopTouchEvent = false;
623         for (const auto& entry : iter->second) {
624             auto recognizer = AceType::DynamicCast<NG::NGGestureRecognizer>(entry);
625             if (recognizer) {
626                 entry->HandleMultiContainerEvent(point);
627                 eventTree_.AddGestureProcedure(reinterpret_cast<uintptr_t>(AceType::RawPtr(recognizer)), point,
628                     NG::TransRefereeState(recognizer->GetRefereeState()),
629                     NG::TransGestureDisposal(recognizer->GetGestureDisposal()));
630             }
631             if (!recognizer && !isStopTouchEvent) {
632                 isStopTouchEvent = !entry->HandleMultiContainerEvent(point);
633                 eventTree_.AddGestureProcedure(reinterpret_cast<uintptr_t>(AceType::RawPtr(entry)),
634                     std::string("Handle").append(GestureSnapshot::TransTouchType(point.type)), "", "");
635             }
636         }
637     }
638 
639     if (point.type == TouchType::UP || point.type == TouchType::CANCEL) {
640         postEventRefereeNG_->CleanGestureScope(point.id);
641         postEventTouchTestResults_.erase(point.id);
642         if (postEventTouchTestResults_.empty()) {
643             postEventRefereeNG_->CleanRedundanceScope();
644         }
645     }
646     return true;
647 }
648 
DispatchTouchEvent(const AxisEvent & event)649 bool EventManager::DispatchTouchEvent(const AxisEvent& event)
650 {
651     ContainerScope scope(instanceId_);
652 
653     const auto curResultIter = axisTouchTestResults_.find(event.id);
654     if (curResultIter == axisTouchTestResults_.end()) {
655         LOGI("the %{public}d axis test result does not exist!", event.id);
656         return false;
657     }
658     if (event.action == AxisAction::BEGIN) {
659         // first collect gesture into gesture referee.
660         if (Container::IsCurrentUseNewPipeline()) {
661             if (refereeNG_) {
662                 refereeNG_->AddGestureToScope(event.id, curResultIter->second);
663             }
664         }
665     }
666 
667     ACE_FUNCTION_TRACE();
668     for (const auto& entry : curResultIter->second) {
669         if (!entry->HandleEvent(event)) {
670             break;
671         }
672     }
673     if (event.action == AxisAction::END || event.action == AxisAction::NONE || event.action == AxisAction::CANCEL) {
674         if (Container::IsCurrentUseNewPipeline()) {
675             if (refereeNG_) {
676                 refereeNG_->CleanGestureScope(event.id);
677             }
678         }
679         axisTouchTestResults_.erase(event.id);
680     }
681     lastEventTime_ = event.time;
682     return true;
683 }
684 
DispatchTabIndexEvent(const KeyEvent & event,const RefPtr<FocusNode> & focusNode,const RefPtr<FocusGroup> & mainNode)685 bool EventManager::DispatchTabIndexEvent(
686     const KeyEvent& event, const RefPtr<FocusNode>& focusNode, const RefPtr<FocusGroup>& mainNode)
687 {
688     CHECK_NULL_RETURN(focusNode, false);
689     CHECK_NULL_RETURN(mainNode, false);
690     if (focusNode->HandleFocusByTabIndex(event, mainNode)) {
691         LOGI("Tab index focus system handled this event");
692         return true;
693     }
694     return false;
695 }
696 
DispatchKeyEvent(const KeyEvent & event,const RefPtr<FocusNode> & focusNode)697 bool EventManager::DispatchKeyEvent(const KeyEvent& event, const RefPtr<FocusNode>& focusNode)
698 {
699     CHECK_NULL_RETURN(focusNode, false);
700     if (focusNode->HandleKeyEvent(event)) {
701         LOGI("Default focus system handled this event");
702         return true;
703     }
704     return false;
705 }
706 
DispatchTabIndexEventNG(const KeyEvent & event,const RefPtr<NG::FrameNode> & mainView)707 bool EventManager::DispatchTabIndexEventNG(const KeyEvent& event, const RefPtr<NG::FrameNode>& mainView)
708 {
709     CHECK_NULL_RETURN(mainView, false);
710     TAG_LOGD(AceLogTag::ACE_FOCUS,
711         "Dispatch tab index event: code:%{public}d/action:%{public}d on node: %{public}s/%{public}d.", event.code,
712         event.action, mainView->GetTag().c_str(), mainView->GetId());
713     auto mainViewFocusHub = mainView->GetFocusHub();
714     CHECK_NULL_RETURN(mainViewFocusHub, false);
715     if (mainViewFocusHub->HandleFocusByTabIndex(event)) {
716         TAG_LOGD(AceLogTag::ACE_FOCUS, "Tab index handled the key event: code:%{public}d/action:%{public}d", event.code,
717             event.action);
718         return true;
719     }
720     return false;
721 }
722 
DispatchKeyEventNG(const KeyEvent & event,const RefPtr<NG::FrameNode> & focusNode)723 bool EventManager::DispatchKeyEventNG(const KeyEvent& event, const RefPtr<NG::FrameNode>& focusNode)
724 {
725     CHECK_NULL_RETURN(focusNode, false);
726     TAG_LOGD(AceLogTag::ACE_FOCUS,
727         "Dispatch key event: code:%{public}d/action:%{public}d on node: %{public}s/%{public}d.", event.code,
728         event.action, focusNode->GetTag().c_str(), focusNode->GetId());
729     auto focusNodeHub = focusNode->GetFocusHub();
730     CHECK_NULL_RETURN(focusNodeHub, false);
731     if (focusNodeHub->HandleKeyEvent(event)) {
732         TAG_LOGI(AceLogTag::ACE_FOCUS, "Focus system handled the key event: code:%{public}d/action:%{public}d",
733             event.code, event.action);
734         return true;
735     }
736     TAG_LOGD(AceLogTag::ACE_FOCUS, "Focus system do not handled the key event: code:%{public}d/action:%{public}d",
737         event.code, event.action);
738     return false;
739 }
740 
MouseTest(const MouseEvent & event,const RefPtr<RenderNode> & renderNode)741 void EventManager::MouseTest(const MouseEvent& event, const RefPtr<RenderNode>& renderNode)
742 {
743     CHECK_NULL_VOID(renderNode);
744     const Point point { event.x, event.y };
745     MouseHoverTestList hitTestResult;
746     WeakPtr<RenderNode> hoverNode = nullptr;
747     renderNode->MouseDetect(point, point, hitTestResult, hoverNode);
748 
749     if (event.action == MouseAction::WINDOW_LEAVE) {
750         mouseHoverTestResultsPre_ = std::move(mouseHoverTestResults_);
751         mouseHoverTestResults_.clear();
752     } else if (event.action == MouseAction::WINDOW_ENTER) {
753         mouseHoverTestResultsPre_.clear();
754         mouseHoverTestResults_ = std::move(hitTestResult);
755     } else {
756         mouseHoverTestResultsPre_ = std::move(mouseHoverTestResults_);
757         mouseHoverTestResults_ = std::move(hitTestResult);
758     }
759     mouseHoverNodePre_ = mouseHoverNode_;
760     mouseHoverNode_ = hoverNode;
761     LOGI("MouseDetect hit test last/new result size = %{public}zu/%{public}zu", mouseHoverTestResultsPre_.size(),
762         mouseHoverTestResults_.size());
763 }
764 
DispatchMouseEvent(const MouseEvent & event)765 bool EventManager::DispatchMouseEvent(const MouseEvent& event)
766 {
767     if (event.action == MouseAction::PRESS || event.action == MouseAction::RELEASE ||
768         event.action == MouseAction::MOVE) {
769         for (const auto& wp : mouseHoverTestResults_) {
770             auto hoverNode = wp.Upgrade();
771             if (hoverNode) {
772                 if (hoverNode->HandleMouseEvent(event)) {
773                     LOGI("Do HandleMouseEvent. Dispatch node: %{public}s", AceType::TypeName(hoverNode));
774                     break;
775                 }
776             }
777         }
778         return true;
779     }
780     return false;
781 }
782 
DispatchMouseHoverAnimation(const MouseEvent & event)783 void EventManager::DispatchMouseHoverAnimation(const MouseEvent& event)
784 {
785     auto hoverNodeCur = mouseHoverNode_.Upgrade();
786     auto hoverNodePre = mouseHoverNodePre_.Upgrade();
787     if (event.action == MouseAction::PRESS) {
788         if (hoverNodeCur) {
789             hoverNodeCur->AnimateMouseHoverExit();
790         }
791     } else if (event.action == MouseAction::RELEASE) {
792         if (hoverNodeCur) {
793             hoverNodeCur->AnimateMouseHoverEnter();
794         }
795     } else if (event.button == MouseButton::NONE_BUTTON && event.action == MouseAction::MOVE) {
796         if (hoverNodeCur != hoverNodePre) {
797             if (hoverNodeCur) {
798                 hoverNodeCur->AnimateMouseHoverEnter();
799             }
800             if (hoverNodePre) {
801                 hoverNodePre->AnimateMouseHoverExit();
802             }
803         }
804     } else if (event.action == MouseAction::WINDOW_ENTER) {
805         if (hoverNodeCur) {
806             hoverNodeCur->AnimateMouseHoverEnter();
807         }
808     } else if (event.action == MouseAction::WINDOW_LEAVE) {
809         if (hoverNodeCur) {
810             hoverNodeCur->AnimateMouseHoverExit();
811         }
812     }
813 }
814 
DispatchMouseHoverEvent(const MouseEvent & event)815 bool EventManager::DispatchMouseHoverEvent(const MouseEvent& event)
816 {
817     for (const auto& wp : mouseHoverTestResultsPre_) {
818         // get all previous hover nodes while it's not in current hover nodes. Those nodes exit hover
819         auto it = std::find(mouseHoverTestResults_.begin(), mouseHoverTestResults_.end(), wp);
820         if (it == mouseHoverTestResults_.end()) {
821             auto hoverNode = wp.Upgrade();
822             if (hoverNode) {
823                 hoverNode->HandleMouseHoverEvent(MouseState::NONE);
824             }
825         }
826     }
827     for (const auto& wp : mouseHoverTestResults_) {
828         // get all current hover nodes while it's not in previous hover nodes. Those nodes are new hover
829         auto it = std::find(mouseHoverTestResultsPre_.begin(), mouseHoverTestResultsPre_.end(), wp);
830         if (it == mouseHoverTestResultsPre_.end()) {
831             auto hoverNode = wp.Upgrade();
832             if (hoverNode) {
833                 hoverNode->HandleMouseHoverEvent(MouseState::HOVER);
834             }
835         }
836     }
837     return true;
838 }
839 
LogPrintMouseTest()840 void EventManager::LogPrintMouseTest()
841 {
842     if (!SystemProperties::GetDebugEnabled()) {
843         return;
844     }
845     if (currMouseTestResults_.empty()) {
846         TAG_LOGI(AceLogTag::ACE_MOUSE, "Mouse test onMouse result is empty.");
847     } else {
848         for (const auto& result : currMouseTestResults_) {
849             TAG_LOGI(AceLogTag::ACE_MOUSE, "Mouse test onMouse result: %{public}s/%{public}d.",
850                 result->GetNodeName().c_str(), result->GetNodeId());
851         }
852     }
853     if (lastHoverTestResults_.empty()) {
854         TAG_LOGI(AceLogTag::ACE_MOUSE, "Mouse test onHover last result is empty.");
855     } else {
856         for (const auto& result : lastHoverTestResults_) {
857             TAG_LOGI(AceLogTag::ACE_MOUSE, "Mouse test onHover last result: %{public}s/%{public}d.",
858                 result->GetNodeName().c_str(), result->GetNodeId());
859         }
860     }
861     if (currHoverTestResults_.empty()) {
862         TAG_LOGI(AceLogTag::ACE_MOUSE, "Mouse test onHover current result is empty.");
863     } else {
864         for (const auto& result : currHoverTestResults_) {
865             TAG_LOGI(AceLogTag::ACE_MOUSE, "Mouse test onHover current result: %{public}s/%{public}d.",
866                 result->GetNodeName().c_str(), result->GetNodeId());
867         }
868     }
869     auto lastNode = lastHoverNode_.Upgrade();
870     auto currNode = currHoverNode_.Upgrade();
871     TAG_LOGI(AceLogTag::ACE_MOUSE,
872         "Mouse test last/current hoverEffect node: %{public}s/%{public}d / %{public}s/%{public}d",
873         lastNode ? lastNode->GetTag().c_str() : "NULL", lastNode ? lastNode->GetId() : -1,
874         currNode ? currNode->GetTag().c_str() : "NULL", currNode ? currNode->GetId() : -1);
875 }
876 
MouseTest(const MouseEvent & event,const RefPtr<NG::FrameNode> & frameNode,TouchRestrict & touchRestrict)877 void EventManager::MouseTest(
878     const MouseEvent& event, const RefPtr<NG::FrameNode>& frameNode, TouchRestrict& touchRestrict)
879 {
880     TAG_LOGD(AceLogTag::ACE_MOUSE,
881         "Mouse test start. Event is (%{public}f,%{public}f), button: %{public}d, action: %{public}d", event.x, event.y,
882         event.button, event.action);
883     CHECK_NULL_VOID(frameNode);
884     const NG::PointF point { event.x, event.y };
885     TouchTestResult testResult;
886     if (frameNode->HaveSecurityComponent()) {
887         std::vector<NG::RectF> rect;
888         frameNode->CheckSecurityComponentStatus(rect);
889     }
890     frameNode->TouchTest(point, point, point, touchRestrict, testResult, event.GetId());
891 
892     currMouseTestResults_.clear();
893     HoverTestResult hoverTestResult;
894     WeakPtr<NG::FrameNode> hoverNode = nullptr;
895     for (const auto& result : testResult) {
896         auto mouseResult = AceType::DynamicCast<MouseEventTarget>(result);
897         if (mouseResult) {
898             currMouseTestResults_.emplace_back(mouseResult);
899         }
900         auto hoverResult = AceType::DynamicCast<HoverEventTarget>(result);
901         if (hoverResult) {
902             hoverTestResult.emplace_back(hoverResult);
903         }
904         if (!hoverNode.Upgrade()) {
905             auto hoverEffectResult = AceType::DynamicCast<HoverEffectTarget>(result);
906             if (hoverEffectResult) {
907                 hoverNode = hoverEffectResult->GetHoverNode();
908             }
909         }
910     }
911     if (event.action == MouseAction::WINDOW_LEAVE) {
912         TAG_LOGI(AceLogTag::ACE_MOUSE, "Exit hover by leave-window event.");
913         lastHoverTestResults_ = std::move(currHoverTestResults_);
914         currHoverTestResults_.clear();
915     } else if (event.action == MouseAction::WINDOW_ENTER) {
916         TAG_LOGI(AceLogTag::ACE_MOUSE, "Enter hover by enter-window event.");
917         lastHoverTestResults_.clear();
918         currHoverTestResults_ = std::move(hoverTestResult);
919     } else {
920         lastHoverTestResults_ = std::move(currHoverTestResults_);
921         currHoverTestResults_ = std::move(hoverTestResult);
922     }
923     lastHoverNode_ = currHoverNode_;
924     currHoverNode_ = hoverNode;
925     LogPrintMouseTest();
926 }
927 
DispatchMouseEventNG(const MouseEvent & event)928 bool EventManager::DispatchMouseEventNG(const MouseEvent& event)
929 {
930     if (event.action == MouseAction::PRESS || event.action == MouseAction::RELEASE ||
931         event.action == MouseAction::MOVE || event.action == MouseAction::WINDOW_ENTER ||
932         event.action == MouseAction::WINDOW_LEAVE) {
933         MouseTestResult handledResults;
934         handledResults.clear();
935         auto container = Container::Current();
936         CHECK_NULL_RETURN(container, false);
937         if (event.button == MouseButton::LEFT_BUTTON) {
938             for (const auto& mouseTarget : pressMouseTestResults_) {
939                 if (mouseTarget) {
940                     handledResults.emplace_back(mouseTarget);
941                     if (mouseTarget->HandleMouseEvent(event)) {
942                         break;
943                     }
944                 }
945             }
946             if (event.action == MouseAction::PRESS) {
947                 pressMouseTestResults_ = currMouseTestResults_;
948             } else if (event.action == MouseAction::RELEASE) {
949                 DoMouseActionRelease();
950             }
951         }
952         if (event.pullAction == MouseAction::PULL_UP) {
953             DoMouseActionRelease();
954         }
955         for (const auto& mouseTarget : currMouseTestResults_) {
956             if (mouseTarget &&
957                 std::find(handledResults.begin(), handledResults.end(), mouseTarget) == handledResults.end()) {
958                 if (mouseTarget->HandleMouseEvent(event)) {
959                     return true;
960                 }
961             }
962         }
963     }
964     return false;
965 }
966 
DoMouseActionRelease()967 void EventManager::DoMouseActionRelease()
968 {
969     pressMouseTestResults_.clear();
970 }
971 
DispatchMouseHoverAnimationNG(const MouseEvent & event)972 void EventManager::DispatchMouseHoverAnimationNG(const MouseEvent& event)
973 {
974     auto hoverNodeCur = currHoverNode_.Upgrade();
975     auto hoverNodePre = lastHoverNode_.Upgrade();
976     if (event.action == MouseAction::PRESS) {
977         if (hoverNodeCur) {
978             hoverNodeCur->AnimateHoverEffect(false);
979         }
980     } else if (event.action == MouseAction::RELEASE) {
981         if (hoverNodeCur) {
982             hoverNodeCur->AnimateHoverEffect(true);
983         }
984     } else if (event.button == MouseButton::NONE_BUTTON && event.action == MouseAction::MOVE) {
985         if (hoverNodeCur != hoverNodePre) {
986             if (hoverNodeCur) {
987                 hoverNodeCur->AnimateHoverEffect(true);
988             }
989             if (hoverNodePre) {
990                 hoverNodePre->AnimateHoverEffect(false);
991             }
992         }
993     } else if (event.action == MouseAction::WINDOW_ENTER) {
994         if (hoverNodeCur) {
995             hoverNodeCur->AnimateHoverEffect(true);
996         }
997     } else if (event.action == MouseAction::WINDOW_LEAVE) {
998         if (hoverNodeCur) {
999             hoverNodeCur->AnimateHoverEffect(false);
1000         }
1001     }
1002 }
1003 
DispatchMouseHoverEventNG(const MouseEvent & event)1004 bool EventManager::DispatchMouseHoverEventNG(const MouseEvent& event)
1005 {
1006     auto lastHoverEndNode = lastHoverTestResults_.begin();
1007     auto currHoverEndNode = currHoverTestResults_.begin();
1008     RefPtr<HoverEventTarget> lastHoverEndNodeTarget;
1009     uint32_t iterCountLast = 0;
1010     uint32_t iterCountCurr = 0;
1011     for (const auto& hoverResult : lastHoverTestResults_) {
1012         // get valid part of previous hover nodes while it's not in current hover nodes. Those nodes exit hover
1013         // there may have some nodes in currHoverTestResults_ but intercepted
1014         iterCountLast++;
1015         if (lastHoverEndNode != currHoverTestResults_.end()) {
1016             lastHoverEndNode++;
1017         }
1018         if (std::find(currHoverTestResults_.begin(), currHoverTestResults_.end(), hoverResult) ==
1019             currHoverTestResults_.end()) {
1020             hoverResult->HandleHoverEvent(false, event);
1021         }
1022         if ((iterCountLast >= lastHoverDispatchLength_) && (lastHoverDispatchLength_ != 0)) {
1023             lastHoverEndNodeTarget = hoverResult;
1024             break;
1025         }
1026     }
1027     lastHoverDispatchLength_ = 0;
1028     for (const auto& hoverResult : currHoverTestResults_) {
1029         // get valid part of current hover nodes while it's not in previous hover nodes. Those nodes are new hover
1030         // the valid part stops at first interception
1031         iterCountCurr++;
1032         if (currHoverEndNode != currHoverTestResults_.end()) {
1033             currHoverEndNode++;
1034         }
1035         if (std::find(lastHoverTestResults_.begin(), lastHoverEndNode, hoverResult) == lastHoverEndNode) {
1036             if (!hoverResult->HandleHoverEvent(true, event)) {
1037                 lastHoverDispatchLength_ = iterCountCurr;
1038                 break;
1039             }
1040         }
1041         if (hoverResult == lastHoverEndNodeTarget) {
1042             lastHoverDispatchLength_ = iterCountCurr;
1043             break;
1044         }
1045     }
1046     for (auto hoverResultIt = lastHoverTestResults_.begin(); hoverResultIt != lastHoverEndNode; ++hoverResultIt) {
1047         // there may have previous hover nodes in the invalid part of current hover nodes. Those nodes exit hover also
1048         if (std::find(currHoverEndNode, currHoverTestResults_.end(), *hoverResultIt) != currHoverTestResults_.end()) {
1049             (*hoverResultIt)->HandleHoverEvent(false, event);
1050         }
1051     }
1052     return true;
1053 }
1054 
AxisTest(const AxisEvent & event,const RefPtr<RenderNode> & renderNode)1055 void EventManager::AxisTest(const AxisEvent& event, const RefPtr<RenderNode>& renderNode)
1056 {
1057     CHECK_NULL_VOID(renderNode);
1058     const Point point { event.x, event.y };
1059     WeakPtr<RenderNode> axisNode = nullptr;
1060     renderNode->AxisDetect(point, point, axisNode, event.GetDirection());
1061     axisNode_ = axisNode;
1062     LOGI("Current axis node is %{public}s", AceType::TypeName(axisNode_.Upgrade()));
1063 }
1064 
DispatchAxisEvent(const AxisEvent & event)1065 bool EventManager::DispatchAxisEvent(const AxisEvent& event)
1066 {
1067     auto responseNode = axisNode_.Upgrade();
1068     if (responseNode) {
1069         responseNode->HandleAxisEvent(event);
1070     }
1071     return true;
1072 }
1073 
AxisTest(const AxisEvent & event,const RefPtr<NG::FrameNode> & frameNode)1074 void EventManager::AxisTest(const AxisEvent& event, const RefPtr<NG::FrameNode>& frameNode)
1075 {
1076     CHECK_NULL_VOID(frameNode);
1077     const NG::PointF point { event.x, event.y };
1078     frameNode->AxisTest(point, point, axisTestResults_);
1079 }
1080 
DispatchAxisEventNG(const AxisEvent & event)1081 bool EventManager::DispatchAxisEventNG(const AxisEvent& event)
1082 {
1083     if (event.horizontalAxis == 0 && event.verticalAxis == 0 && event.pinchAxisScale == 0) {
1084         return false;
1085     }
1086     for (const auto& axisTarget : axisTestResults_) {
1087         if (axisTarget && axisTarget->HandleAxisEvent(event)) {
1088             return true;
1089         }
1090     }
1091     return true;
1092 }
1093 
DispatchRotationEvent(const RotationEvent & event,const RefPtr<RenderNode> & renderNode,const RefPtr<RenderNode> & requestFocusNode)1094 bool EventManager::DispatchRotationEvent(
1095     const RotationEvent& event, const RefPtr<RenderNode>& renderNode, const RefPtr<RenderNode>& requestFocusNode)
1096 {
1097     CHECK_NULL_RETURN(renderNode, false);
1098     if (requestFocusNode && renderNode->RotationMatchTest(requestFocusNode)) {
1099         return requestFocusNode->RotationTestForward(event);
1100     } else {
1101         return renderNode->RotationTest(event);
1102     }
1103 }
1104 
AddKeyboardShortcutNode(const WeakPtr<NG::FrameNode> & node)1105 void EventManager::AddKeyboardShortcutNode(const WeakPtr<NG::FrameNode>& node)
1106 {
1107     auto frameNode = node.Upgrade();
1108     CHECK_NULL_VOID(frameNode);
1109     auto iter = keyboardShortcutNode_.begin();
1110     while (iter != keyboardShortcutNode_.end()) {
1111         auto keyboardShortcutNode = (*iter).Upgrade();
1112         if (!keyboardShortcutNode) {
1113             keyboardShortcutNode_.erase(iter++);
1114             continue;
1115         }
1116         if (keyboardShortcutNode->GetId() == frameNode->GetId()) {
1117             return;
1118         }
1119         ++iter;
1120     }
1121     keyboardShortcutNode_.emplace_back(node);
1122 }
1123 
GetKeyboardShortcutKeys(const std::vector<ModifierKey> & keys)1124 uint8_t EventManager::GetKeyboardShortcutKeys(const std::vector<ModifierKey>& keys)
1125 {
1126     uint8_t keyValue = 0;
1127     uint8_t ctrlTimes = 0;
1128     uint8_t shiftTimes = 0;
1129     uint8_t altTimes = 0;
1130     if (keys.size() > KEYS_MAX_VALUE) {
1131         return 0;
1132     }
1133     for (const auto& key : keys) {
1134         switch (static_cast<uint8_t>(key)) {
1135             case static_cast<uint8_t>(ModifierKey::CTRL): {
1136                 keyValue |= static_cast<uint8_t>(CtrlKeysBit::CTRL);
1137                 ++ctrlTimes;
1138                 break;
1139             }
1140             case static_cast<uint8_t>(ModifierKey::SHIFT): {
1141                 keyValue |= static_cast<uint8_t>(CtrlKeysBit::SHIFT);
1142                 ++shiftTimes;
1143                 break;
1144             }
1145             case static_cast<uint8_t>(ModifierKey::ALT): {
1146                 keyValue |= static_cast<uint8_t>(CtrlKeysBit::ALT);
1147                 ++altTimes;
1148                 break;
1149             }
1150             default:
1151                 keyValue |= 0;
1152         }
1153     }
1154     if (ctrlTimes > 1 || shiftTimes > 1 || altTimes > 1) {
1155         return 0;
1156     }
1157     return keyValue;
1158 }
1159 
IsSystemKeyboardShortcut(const std::string & value,uint8_t keys)1160 bool EventManager::IsSystemKeyboardShortcut(const std::string& value, uint8_t keys)
1161 {
1162     if (!(keys ^ static_cast<uint8_t>(CtrlKeysBit::CTRL)) && value == SHORT_CUT_VALUE_C) {
1163         return true;
1164     }
1165     if (!(keys ^ static_cast<uint8_t>(CtrlKeysBit::CTRL)) && value == SHORT_CUT_VALUE_A) {
1166         return true;
1167     }
1168     if (!(keys ^ static_cast<uint8_t>(CtrlKeysBit::CTRL)) && value == SHORT_CUT_VALUE_V) {
1169         return true;
1170     }
1171     if (!(keys ^ static_cast<uint8_t>(CtrlKeysBit::CTRL)) && value == SHORT_CUT_VALUE_X) {
1172         return true;
1173     }
1174     if (!(keys ^ static_cast<uint8_t>(CtrlKeysBit::CTRL)) && value == SHORT_CUT_VALUE_Y) {
1175         return true;
1176     }
1177     if (!(keys ^ static_cast<uint8_t>(CtrlKeysBit::CTRL)) && value == SHORT_CUT_VALUE_Z) {
1178         return true;
1179     }
1180     if (!(keys ^ (static_cast<uint8_t>(CtrlKeysBit::CTRL) + static_cast<uint8_t>(CtrlKeysBit::SHIFT))) &&
1181         value == SHORT_CUT_VALUE_Z) {
1182         return true;
1183     }
1184     return false;
1185 }
1186 
IsSameKeyboardShortcutNode(const std::string & value,uint8_t keys)1187 bool EventManager::IsSameKeyboardShortcutNode(const std::string& value, uint8_t keys)
1188 {
1189     if (IsSystemKeyboardShortcut(value, keys)) {
1190         return true;
1191     }
1192     for (auto& weakNode : keyboardShortcutNode_) {
1193         auto frameNode = weakNode.Upgrade();
1194         if (!frameNode) {
1195             continue;
1196         }
1197         auto eventHub = frameNode->GetEventHub<NG::EventHub>();
1198         if (!eventHub) {
1199             continue;
1200         }
1201         auto keyboardShortcuts = eventHub->GetKeyboardShortcut();
1202         for (auto& keyboardShortcut : keyboardShortcuts) {
1203             if (keyboardShortcut.value.find(value) != std::string::npos && keyboardShortcut.keys == keys) {
1204                 return true;
1205             }
1206         }
1207     }
1208     return false;
1209 }
1210 
AddKeyboardShortcutSingleKey(uint8_t keys,std::vector<std::vector<KeyCode>> & keyCodes,std::vector<uint8_t> & permutation)1211 void AddKeyboardShortcutSingleKey(
1212     uint8_t keys, std::vector<std::vector<KeyCode>>& keyCodes, std::vector<uint8_t>& permutation)
1213 {
1214     uint8_t index = 0;
1215     std::vector<KeyCode> keyCode1;
1216     std::vector<KeyCode> keyCode2;
1217     if (keys & static_cast<uint8_t>(CtrlKeysBit::CTRL)) {
1218         keyCode1.emplace_back(KeyCode::KEY_CTRL_LEFT);
1219         keyCode2.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1220         permutation.emplace_back(++index);
1221     }
1222     if (keys & static_cast<uint8_t>(CtrlKeysBit::SHIFT)) {
1223         keyCode1.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1224         keyCode2.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1225         permutation.emplace_back(++index);
1226     }
1227     if (keys & static_cast<uint8_t>(CtrlKeysBit::ALT)) {
1228         keyCode1.emplace_back(KeyCode::KEY_ALT_LEFT);
1229         keyCode2.emplace_back(KeyCode::KEY_ALT_RIGHT);
1230         permutation.emplace_back(++index);
1231     }
1232     keyCodes.emplace_back(keyCode1);
1233     keyCodes.emplace_back(keyCode2);
1234 }
1235 
AddKeyboardShortcutDoubleKeysWithCtrlShift(uint8_t keys,std::vector<std::vector<KeyCode>> & keyCodes,std::vector<uint8_t> & permutation)1236 void AddKeyboardShortcutDoubleKeysWithCtrlShift(
1237     uint8_t keys, std::vector<std::vector<KeyCode>>& keyCodes, std::vector<uint8_t>& permutation)
1238 {
1239     uint8_t index = 0;
1240     std::vector<KeyCode> keyCode1;
1241     std::vector<KeyCode> keyCode2;
1242     std::vector<KeyCode> keyCode3;
1243     std::vector<KeyCode> keyCode4;
1244 
1245     keyCode1.emplace_back(KeyCode::KEY_CTRL_LEFT);
1246     keyCode2.emplace_back(KeyCode::KEY_CTRL_LEFT);
1247     keyCode3.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1248     keyCode4.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1249     permutation.emplace_back(++index);
1250 
1251     keyCode1.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1252     keyCode2.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1253     keyCode3.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1254     keyCode4.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1255     permutation.emplace_back(++index);
1256 
1257     keyCodes.emplace_back(keyCode1);
1258     keyCodes.emplace_back(keyCode2);
1259     keyCodes.emplace_back(keyCode3);
1260     keyCodes.emplace_back(keyCode4);
1261 }
1262 
AddKeyboardShortcutDoubleKeysWithCtrlAlt(uint8_t keys,std::vector<std::vector<KeyCode>> & keyCodes,std::vector<uint8_t> & permutation)1263 void AddKeyboardShortcutDoubleKeysWithCtrlAlt(
1264     uint8_t keys, std::vector<std::vector<KeyCode>>& keyCodes, std::vector<uint8_t>& permutation)
1265 {
1266     uint8_t index = 0;
1267     std::vector<KeyCode> keyCode1;
1268     std::vector<KeyCode> keyCode2;
1269     std::vector<KeyCode> keyCode3;
1270     std::vector<KeyCode> keyCode4;
1271 
1272     keyCode1.emplace_back(KeyCode::KEY_CTRL_LEFT);
1273     keyCode2.emplace_back(KeyCode::KEY_CTRL_LEFT);
1274     keyCode3.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1275     keyCode4.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1276     permutation.emplace_back(++index);
1277 
1278     keyCode1.emplace_back(KeyCode::KEY_ALT_LEFT);
1279     keyCode2.emplace_back(KeyCode::KEY_ALT_RIGHT);
1280     keyCode3.emplace_back(KeyCode::KEY_ALT_LEFT);
1281     keyCode4.emplace_back(KeyCode::KEY_ALT_RIGHT);
1282     permutation.emplace_back(++index);
1283 
1284     keyCodes.emplace_back(keyCode1);
1285     keyCodes.emplace_back(keyCode2);
1286     keyCodes.emplace_back(keyCode3);
1287     keyCodes.emplace_back(keyCode4);
1288 }
1289 
AddKeyboardShortcutDoubleKeysWithShiftAlt(uint8_t keys,std::vector<std::vector<KeyCode>> & keyCodes,std::vector<uint8_t> & permutation)1290 void AddKeyboardShortcutDoubleKeysWithShiftAlt(
1291     uint8_t keys, std::vector<std::vector<KeyCode>>& keyCodes, std::vector<uint8_t>& permutation)
1292 {
1293     uint8_t index = 0;
1294     std::vector<KeyCode> keyCode1;
1295     std::vector<KeyCode> keyCode2;
1296     std::vector<KeyCode> keyCode3;
1297     std::vector<KeyCode> keyCode4;
1298 
1299     keyCode1.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1300     keyCode2.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1301     keyCode3.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1302     keyCode4.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1303     permutation.emplace_back(++index);
1304 
1305     keyCode1.emplace_back(KeyCode::KEY_ALT_LEFT);
1306     keyCode2.emplace_back(KeyCode::KEY_ALT_RIGHT);
1307     keyCode3.emplace_back(KeyCode::KEY_ALT_LEFT);
1308     keyCode4.emplace_back(KeyCode::KEY_ALT_RIGHT);
1309     permutation.emplace_back(++index);
1310 
1311     keyCodes.emplace_back(keyCode1);
1312     keyCodes.emplace_back(keyCode2);
1313     keyCodes.emplace_back(keyCode3);
1314     keyCodes.emplace_back(keyCode4);
1315 }
1316 
AddKeyboardShortcutDoubleKeys(uint8_t keys,std::vector<std::vector<KeyCode>> & keyCodes,std::vector<uint8_t> & permutation)1317 void AddKeyboardShortcutDoubleKeys(
1318     uint8_t keys, std::vector<std::vector<KeyCode>>& keyCodes, std::vector<uint8_t>& permutation)
1319 {
1320     if (keys == static_cast<uint8_t>(CtrlKeysBit::CTRL) + static_cast<uint8_t>(CtrlKeysBit::SHIFT)) {
1321         AddKeyboardShortcutDoubleKeysWithCtrlShift(keys, keyCodes, permutation);
1322     }
1323     if (keys == static_cast<uint8_t>(CtrlKeysBit::CTRL) + static_cast<uint8_t>(CtrlKeysBit::ALT)) {
1324         AddKeyboardShortcutDoubleKeysWithCtrlAlt(keys, keyCodes, permutation);
1325     }
1326     if (keys == static_cast<uint8_t>(CtrlKeysBit::SHIFT) + static_cast<uint8_t>(CtrlKeysBit::ALT)) {
1327         AddKeyboardShortcutDoubleKeysWithShiftAlt(keys, keyCodes, permutation);
1328     }
1329 }
1330 
AddKeyboardShortcutTripleKeys(uint8_t keys,std::vector<std::vector<KeyCode>> & keyCodes,std::vector<uint8_t> & permutation)1331 void AddKeyboardShortcutTripleKeys(
1332     uint8_t keys, std::vector<std::vector<KeyCode>>& keyCodes, std::vector<uint8_t>& permutation)
1333 {
1334     uint8_t index = 0;
1335     std::vector<KeyCode> keyCode1;
1336     std::vector<KeyCode> keyCode2;
1337     std::vector<KeyCode> keyCode3;
1338     std::vector<KeyCode> keyCode4;
1339     std::vector<KeyCode> keyCode5;
1340     std::vector<KeyCode> keyCode6;
1341     std::vector<KeyCode> keyCode7;
1342     std::vector<KeyCode> keyCode8;
1343 
1344     keyCode1.emplace_back(KeyCode::KEY_CTRL_LEFT);
1345     keyCode2.emplace_back(KeyCode::KEY_CTRL_LEFT);
1346     keyCode3.emplace_back(KeyCode::KEY_CTRL_LEFT);
1347     keyCode4.emplace_back(KeyCode::KEY_CTRL_LEFT);
1348     keyCode5.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1349     keyCode6.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1350     keyCode7.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1351     keyCode8.emplace_back(KeyCode::KEY_CTRL_RIGHT);
1352     permutation.emplace_back(++index);
1353 
1354     keyCode1.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1355     keyCode2.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1356     keyCode3.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1357     keyCode4.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1358     keyCode5.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1359     keyCode6.emplace_back(KeyCode::KEY_SHIFT_LEFT);
1360     keyCode7.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1361     keyCode8.emplace_back(KeyCode::KEY_SHIFT_RIGHT);
1362     permutation.emplace_back(++index);
1363 
1364     keyCode1.emplace_back(KeyCode::KEY_ALT_LEFT);
1365     keyCode2.emplace_back(KeyCode::KEY_ALT_RIGHT);
1366     keyCode3.emplace_back(KeyCode::KEY_ALT_LEFT);
1367     keyCode4.emplace_back(KeyCode::KEY_ALT_RIGHT);
1368     keyCode5.emplace_back(KeyCode::KEY_ALT_LEFT);
1369     keyCode6.emplace_back(KeyCode::KEY_ALT_RIGHT);
1370     keyCode7.emplace_back(KeyCode::KEY_ALT_LEFT);
1371     keyCode8.emplace_back(KeyCode::KEY_ALT_RIGHT);
1372     permutation.emplace_back(++index);
1373 
1374     keyCodes.emplace_back(keyCode1);
1375     keyCodes.emplace_back(keyCode2);
1376     keyCodes.emplace_back(keyCode3);
1377     keyCodes.emplace_back(keyCode4);
1378     keyCodes.emplace_back(keyCode5);
1379     keyCodes.emplace_back(keyCode6);
1380     keyCodes.emplace_back(keyCode7);
1381     keyCodes.emplace_back(keyCode8);
1382 }
1383 
AddKeyboardShortcutKeys(uint8_t keys,std::vector<std::vector<KeyCode>> & keyCodes,std::vector<uint8_t> & permutation)1384 void AddKeyboardShortcutKeys(
1385     uint8_t keys, std::vector<std::vector<KeyCode>>& keyCodes, std::vector<uint8_t>& permutation)
1386 {
1387     // single FunctionKey
1388     if (keys == 0) {
1389         keyCodes.emplace_back(std::vector<KeyCode>());
1390     }
1391     // single key
1392     if (keys == static_cast<uint8_t>(CtrlKeysBit::CTRL) || keys == static_cast<uint8_t>(CtrlKeysBit::SHIFT) ||
1393         keys == static_cast<uint8_t>(CtrlKeysBit::ALT)) {
1394         LOGI("AddKeyboardShortcutKeys single key");
1395         AddKeyboardShortcutSingleKey(keys, keyCodes, permutation);
1396     }
1397     // double keys
1398     if (keys == static_cast<uint8_t>(CtrlKeysBit::CTRL) + static_cast<uint8_t>(CtrlKeysBit::SHIFT) ||
1399         keys == static_cast<uint8_t>(CtrlKeysBit::CTRL) + static_cast<uint8_t>(CtrlKeysBit::ALT) ||
1400         keys == static_cast<uint8_t>(CtrlKeysBit::SHIFT) + static_cast<uint8_t>(CtrlKeysBit::ALT)) {
1401         LOGI("AddKeyboardShortcutKeys double keys");
1402         AddKeyboardShortcutDoubleKeys(keys, keyCodes, permutation);
1403     }
1404     // triple keys
1405     if (keys == static_cast<uint8_t>(CtrlKeysBit::CTRL) + static_cast<uint8_t>(CtrlKeysBit::SHIFT) +
1406                     static_cast<uint8_t>(CtrlKeysBit::ALT)) {
1407         LOGI("AddKeyboardShortcutKeys triple keys");
1408         AddKeyboardShortcutTripleKeys(keys, keyCodes, permutation);
1409     }
1410 }
1411 
TriggerKeyboardShortcut(const KeyEvent & event,const std::vector<NG::KeyboardShortcut> & keyboardShortcuts,const WeakPtr<NG::FrameNode> & node,const RefPtr<NG::EventHub> & eventHub)1412 void TriggerKeyboardShortcut(const KeyEvent& event, const std::vector<NG::KeyboardShortcut>& keyboardShortcuts,
1413     const WeakPtr<NG::FrameNode>& node, const RefPtr<NG::EventHub>& eventHub)
1414 {
1415     CHECK_NULL_VOID(eventHub);
1416     for (auto& keyboardShortcut : keyboardShortcuts) {
1417         if (keyboardShortcut.value.empty()) {
1418             continue;
1419         }
1420 
1421         std::vector<std::vector<KeyCode>> keyCodes;
1422         std::vector<uint8_t> permutation;
1423         AddKeyboardShortcutKeys(keyboardShortcut.keys, keyCodes, permutation);
1424         // FunctionKey
1425         if (event.IsFunctionKey() || event.IsEscapeKey()) {
1426             if (event.ConvertInputCodeToString() != keyboardShortcut.value) {
1427                 continue;
1428             }
1429         } else if (event.ConvertInputCodeToString().find(keyboardShortcut.value) == std::string::npos) {
1430             continue;
1431         }
1432         // Handle left and right the keys problem.
1433         std::vector<uint8_t> perm;
1434         for (auto& keyCode : keyCodes) {
1435             perm.assign(permutation.begin(), permutation.end());
1436             // Handle the keys order problem.
1437             do {
1438                 keyCode.emplace_back(event.code);
1439                 if (!event.IsKey(keyCode)) {
1440                     keyCode.pop_back();
1441                     std::next_permutation(keyCode.begin(), keyCode.end());
1442                     continue;
1443                 }
1444 
1445                 if (keyboardShortcut.onKeyboardShortcutAction) {
1446                     keyboardShortcut.onKeyboardShortcutAction();
1447                     LOGI("TriggerKeyboardShortcut action done.");
1448                 } else {
1449                     auto gestureEventHub = eventHub->GetGestureEventHub();
1450                     if (gestureEventHub && gestureEventHub->IsClickable()) {
1451                         gestureEventHub->KeyBoardShortCutClick(event, node);
1452                         LOGI("TriggerKeyboardShortcut click done.");
1453                     }
1454                 }
1455                 keyCode.pop_back();
1456                 std::next_permutation(keyCode.begin(), keyCode.end());
1457             } while (std::next_permutation(perm.begin(), perm.end()));
1458             perm.clear();
1459         }
1460         keyCodes.clear();
1461         permutation.clear();
1462     }
1463 }
1464 
DispatchKeyboardShortcut(const KeyEvent & event)1465 void EventManager::DispatchKeyboardShortcut(const KeyEvent& event)
1466 {
1467     if (event.action != KeyAction::DOWN) {
1468         return;
1469     }
1470     for (auto& node : keyboardShortcutNode_) {
1471         auto frameNode = node.Upgrade();
1472         if (!frameNode || !(frameNode->IsActive())) {
1473             continue;
1474         }
1475         auto eventHub = frameNode->GetEventHub<NG::EventHub>();
1476         if (!eventHub || !(eventHub->IsEnabled())) {
1477             continue;
1478         }
1479 
1480         auto keyboardShortcuts = eventHub->GetKeyboardShortcut();
1481         TriggerKeyboardShortcut(event, keyboardShortcuts, node, eventHub);
1482     }
1483 }
1484 
DelKeyboardShortcutNode(int32_t nodeId)1485 void EventManager::DelKeyboardShortcutNode(int32_t nodeId)
1486 {
1487     auto iter = keyboardShortcutNode_.begin();
1488     while (iter != keyboardShortcutNode_.end()) {
1489         auto frameNode = (*iter).Upgrade();
1490         if (!frameNode) {
1491             keyboardShortcutNode_.erase(iter++);
1492             continue;
1493         }
1494         if (frameNode->GetId() == nodeId) {
1495             keyboardShortcutNode_.erase(iter);
1496             break;
1497         }
1498         ++iter;
1499     }
1500 }
1501 
ClearResults()1502 void EventManager::ClearResults()
1503 {
1504     touchTestResults_.clear();
1505     postEventTouchTestResults_.clear();
1506     mouseTestResults_.clear();
1507     axisTouchTestResults_.clear();
1508     keyboardShortcutNode_.clear();
1509 }
1510 
EventManager()1511 EventManager::EventManager()
1512 {
1513     refereeNG_ = AceType::MakeRefPtr<NG::GestureReferee>();
1514     postEventRefereeNG_ = AceType::MakeRefPtr<NG::GestureReferee>();
1515     referee_ = AceType::MakeRefPtr<GestureReferee>();
1516     responseCtrl_ = AceType::MakeRefPtr<NG::ResponseCtrl>();
1517 
1518     auto callback = [weak = WeakClaim(this)](size_t touchId) -> bool {
1519         auto eventManager = weak.Upgrade();
1520         CHECK_NULL_RETURN(eventManager, false);
1521         auto refereeNG = eventManager->refereeNG_;
1522         CHECK_NULL_RETURN(refereeNG, false);
1523         return refereeNG->HasGestureAccepted(touchId);
1524     };
1525     referee_->SetQueryStateFunc(std::move(callback));
1526 
1527     auto cleanReferee = [weak = WeakClaim(this)](size_t touchId) -> void {
1528         auto eventManager = weak.Upgrade();
1529         CHECK_NULL_VOID(eventManager);
1530         auto referee = eventManager->referee_;
1531         CHECK_NULL_VOID(referee);
1532         auto gestureScope = referee->GetGestureScope();
1533         const auto iter = gestureScope.find(touchId);
1534         if (iter == gestureScope.end()) {
1535             return;
1536         }
1537 
1538         auto highRecognizers = iter->second.GetHighRecognizers();
1539         auto lowRecognizers = iter->second.GetLowRecognizers();
1540         auto parallelRecognizers = iter->second.GetParallelRecognizers();
1541 
1542         for (const auto& weak : highRecognizers) {
1543             auto gesture = weak.Upgrade();
1544             if (gesture) {
1545                 gesture->OnRejected(touchId);
1546             }
1547         }
1548 
1549         for (const auto& weak : lowRecognizers) {
1550             auto gesture = weak.Upgrade();
1551             if (gesture) {
1552                 gesture->OnRejected(touchId);
1553             }
1554         }
1555 
1556         for (const auto& weak : parallelRecognizers) {
1557             auto gesture = weak.Upgrade();
1558             if (gesture) {
1559                 gesture->OnRejected(touchId);
1560             }
1561         }
1562     };
1563     refereeNG_->SetQueryStateFunc(std::move(cleanReferee));
1564 }
1565 
DumpEvent() const1566 void EventManager::DumpEvent() const
1567 {
1568     std::list<std::pair<int32_t, std::string>> dumpList;
1569     eventTree_.Dump(dumpList, 0);
1570     for (auto& item : dumpList) {
1571         DumpLog::GetInstance().Print(item.first, item.second);
1572     }
1573 }
1574 
AddGestureSnapshot(int32_t finger,int32_t depth,const RefPtr<TouchEventTarget> & target)1575 void EventManager::AddGestureSnapshot(int32_t finger, int32_t depth, const RefPtr<TouchEventTarget>& target)
1576 {
1577     if (!target) {
1578         return;
1579     }
1580     RefPtr<GestureSnapshot> info = target->Dump();
1581     auto frameNode = target->GetAttachedNode().Upgrade();
1582     if (frameNode) {
1583         info->nodeId = frameNode->GetId();
1584     }
1585     info->depth = depth;
1586     eventTree_.AddGestureSnapshot(finger, std::move(info));
1587 
1588     // add child gesture if target is group
1589     auto group = AceType::DynamicCast<NG::RecognizerGroup>(target);
1590     if (group) {
1591         for (const auto& child : group->GetGroupRecognizer()) {
1592             AddGestureSnapshot(finger, depth + 1, child);
1593         }
1594     }
1595 }
1596 
SetHittedFrameNode(const std::list<RefPtr<NG::NGGestureRecognizer>> & touchTestResults)1597 void EventManager::SetHittedFrameNode(const std::list<RefPtr<NG::NGGestureRecognizer>>& touchTestResults)
1598 {
1599     if (touchTestResults.empty()) {
1600         return;
1601     }
1602     for (const auto& item : touchTestResults) {
1603         auto node = item->GetAttachedNode().Upgrade();
1604         if (node) {
1605             hittedFrameNode_.emplace(node);
1606         }
1607         auto group = AceType::DynamicCast<NG::RecognizerGroup>(item);
1608         if (group) {
1609             auto groupRecognizers = group->GetGroupRecognizer();
1610             SetHittedFrameNode(groupRecognizers);
1611         }
1612     }
1613 }
1614 
CleanGestureEventHub()1615 void EventManager::CleanGestureEventHub()
1616 {
1617     for (const auto& item : hittedFrameNode_) {
1618         auto frameNode = item.Upgrade();
1619         if (frameNode) {
1620             auto gestureEventHub = frameNode->GetOrCreateGestureEventHub();
1621             if (gestureEventHub) {
1622                 gestureEventHub->CleanExternalRecognizers();
1623             }
1624         }
1625     }
1626     hittedFrameNode_.clear();
1627 }
1628 
1629 } // namespace OHOS::Ace
1630