• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2024 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "key_command_handler.h"
17 
18 #include "ability_manager_client.h"
19 #include "device_event_monitor.h"
20 #include "event_log_helper.h"
21 #include "gesturesense_wrapper.h"
22 #include "input_screen_capture_agent.h"
23 #ifdef SHORTCUT_KEY_MANAGER_ENABLED
24 #include "key_shortcut_manager.h"
25 #endif // SHORTCUT_KEY_MANAGER_ENABLED
26 #include "key_command_handler_util.h"
27 #include "long_press_subscriber_handler.h"
28 #ifndef OHOS_BUILD_ENABLE_WATCH
29 #include "pointer_drawing_manager.h"
30 #endif // OHOS_BUILD_ENABLE_WATCH
31 #include "stylus_key_handler.h"
32 
33 #undef MMI_LOG_DOMAIN
34 #define MMI_LOG_DOMAIN MMI_LOG_HANDLER
35 #undef MMI_LOG_TAG
36 #define MMI_LOG_TAG "KeyCommandHandler"
37 
38 namespace OHOS {
39 namespace MMI {
40 namespace {
41 constexpr float MOVE_TOLERANCE { 3.0f };
42 constexpr float MIN_GESTURE_STROKE_LENGTH { 200.0f };
43 constexpr float MIN_LETTER_GESTURE_SQUARENESS { 0.15f };
44 constexpr float MIN_START_GESTURE { 60.0f };
45 constexpr int32_t POINTER_NUMBER { 2 };
46 constexpr int32_t EVEN_NUMBER { 2 };
47 constexpr int64_t NO_DELAY { 0 };
48 constexpr int64_t FREQUENCY { 1000 };
49 constexpr int64_t TAP_DOWN_INTERVAL_MILLIS { 550000 };
50 constexpr int64_t SOS_INTERVAL_TIMES { 300000 };
51 constexpr int64_t SOS_DELAY_TIMES { 1000000 };
52 constexpr int64_t SOS_COUNT_DOWN_TIMES { 4000000 };
53 constexpr int32_t MAX_TAP_COUNT { 2 };
54 constexpr int32_t ANCO_KNUCKLE_POINTER_ID { 15000 };
55 const char* AIBASE_BUNDLE_NAME { "com.hmos.aibase" };
56 const char* WAKEUP_ABILITY_NAME { "WakeUpExtAbility" };
57 const char* SCREENSHOT_BUNDLE_NAME { "com.hmos.screenshot" };
58 const char* SCREENSHOT_ABILITY_NAME { "com.hmos.screenshot.ServiceExtAbility" };
59 const char* SCREENRECORDER_BUNDLE_NAME { "com.hmos.screenrecorder" };
60 const char* SOS_BUNDLE_NAME { "com.hmos.emergencycommunication" };
61 const char* WALLET_BUNDLE_NAME { "com.hmos.wallet" };
62 constexpr int32_t DEFAULT_VALUE { -1 };
63 constexpr int64_t POWER_ACTION_INTERVAL { 600 };
64 constexpr int64_t SOS_WAIT_TIME { 3000 };
65 const char* PC_PRO_SCREENSHOT_BUNDLE_NAME { "com.hmos.screenshot" };
66 const char* PC_PRO_SCREENSHOT_ABILITY_NAME { "com.hmos.screenshot.ServiceExtAbility" };
67 const char* PC_PRO_SCREENRECORDER_BUNDLE_NAME { "com.hmos.screenrecorder" };
68 const char* PC_PRO_SCREENRECORDER_ABILITY_NAME { "com.hmos.screenrecorder.ServiceExtAbility" };
69 const char* KEY_ENABLE { "enable" };
70 const char* KEY_STATUS { "status" };
71 constexpr size_t DEFAULT_BUFFER_LENGTH { 512 };
72 const std::string SECURE_SETTING_URI_PROXY {
73     "datashare:///com.ohos.settingsdata/entry/settingsdata/USER_SETTINGSDATA_SECURE_%d?Proxy=true" };
74 } // namespace
75 
76 #ifdef OHOS_BUILD_ENABLE_KEYBOARD
HandleKeyEvent(const std::shared_ptr<KeyEvent> keyEvent)77 void KeyCommandHandler::HandleKeyEvent(const std::shared_ptr<KeyEvent> keyEvent)
78 {
79     CHKPV(keyEvent);
80     if (TouchPadKnuckleDoubleClickHandle(keyEvent)) {
81         return;
82     }
83     if (OnHandleEvent(keyEvent)) {
84         if (DISPLAY_MONITOR->GetScreenStatus() == EventFwk::CommonEventSupport::COMMON_EVENT_SCREEN_OFF) {
85             auto monitorHandler = InputHandler->GetMonitorHandler();
86             CHKPV(monitorHandler);
87             keyEvent->SetFourceMonitorFlag(true);
88 #ifndef OHOS_BUILD_EMULATOR
89             monitorHandler->OnHandleEvent(keyEvent);
90 #endif // OHOS_BUILD_EMULATOR
91             keyEvent->SetFourceMonitorFlag(false);
92         }
93         MMI_HILOGD("The keyEvent start launch an ability, keyCode:%{private}d", keyEvent->GetKeyCode());
94         BytraceAdapter::StartBytrace(keyEvent, BytraceAdapter::KEY_LAUNCH_EVENT);
95         return;
96     }
97     CHKPV(nextHandler_);
98     nextHandler_->HandleKeyEvent(keyEvent);
99 }
100 #endif // OHOS_BUILD_ENABLE_KEYBOARD
101 
102 #ifdef OHOS_BUILD_ENABLE_POINTER
HandlePointerEvent(const std::shared_ptr<PointerEvent> pointerEvent)103 void KeyCommandHandler::HandlePointerEvent(const std::shared_ptr<PointerEvent> pointerEvent)
104 {
105     CHKPV(pointerEvent);
106     if (OnHandleEvent(pointerEvent)) {
107         if (EventLogHelper::IsBetaVersion() && !pointerEvent->HasFlag(InputEvent::EVENT_FLAG_PRIVACY_MODE)) {
108             MMI_HILOGD("The pointerEvent start launch an ability, pointAction:%{public}s",
109                 pointerEvent->DumpPointerAction());
110         } else {
111             MMI_HILOGD("The pointerEvent start launch an ability, pointAction:%s", pointerEvent->DumpPointerAction());
112         }
113     }
114     CHKPV(nextHandler_);
115     nextHandler_->HandlePointerEvent(pointerEvent);
116 }
117 #endif // OHOS_BUILD_ENABLE_POINTER
118 
119 #ifdef OHOS_BUILD_ENABLE_TOUCH
HandleTouchEvent(const std::shared_ptr<PointerEvent> pointerEvent)120 void KeyCommandHandler::HandleTouchEvent(const std::shared_ptr<PointerEvent> pointerEvent)
121 {
122     CHKPV(pointerEvent);
123     CHKPV(nextHandler_);
124     OnHandleTouchEvent(pointerEvent);
125     int32_t id = pointerEvent->GetPointerId();
126     PointerEvent::PointerItem item;
127     pointerEvent->GetPointerItem(id, item);
128     int32_t toolType = item.GetToolType();
129     if (toolType == PointerEvent::TOOL_TYPE_KNUCKLE) {
130         pointerEvent->AddFlag(InputEvent::EVENT_FLAG_NO_INTERCEPT);
131     }
132     nextHandler_->HandleTouchEvent(pointerEvent);
133 }
134 #endif // OHOS_BUILD_ENABLE_TOUCH
135 
GetKnuckleSwitchValue()136 bool KeyCommandHandler::GetKnuckleSwitchValue()
137 {
138     return knuckleSwitch_.statusConfigValue;
139 }
140 
SkipKnuckleDetect()141 bool KeyCommandHandler::SkipKnuckleDetect()
142 {
143     return ((!screenshotSwitch_.statusConfigValue) && (!recordSwitch_.statusConfigValue)) ||
144         knuckleSwitch_.statusConfigValue;
145 }
146 
147 #ifdef OHOS_BUILD_ENABLE_TOUCH
OnHandleTouchEvent(const std::shared_ptr<PointerEvent> touchEvent)148 void KeyCommandHandler::OnHandleTouchEvent(const std::shared_ptr<PointerEvent> touchEvent)
149 {
150     CALL_DEBUG_ENTER;
151     CHKPV(touchEvent);
152     STYLUS_HANDLER->SetLastEventState(false);
153     if (!isParseConfig_) {
154         if (!ParseConfig()) {
155             MMI_HILOGE("Parse configFile failed");
156             return;
157         }
158         isParseConfig_ = true;
159     }
160     if (!isParseLongPressConfig_) {
161         if (!ParseLongPressConfig()) {
162             MMI_HILOGE("Parse long press configFile failed");
163         }
164         isParseLongPressConfig_ = true;
165     }
166     if (!isTimeConfig_) {
167         SetKnuckleDoubleTapIntervalTime(DOUBLE_CLICK_INTERVAL_TIME_DEFAULT);
168         isTimeConfig_ = true;
169     }
170     if (!isDistanceConfig_) {
171         distanceDefaultConfig_ = DOUBLE_CLICK_DISTANCE_DEFAULT_CONFIG * VPR_CONFIG;
172         distanceLongConfig_ = DOUBLE_CLICK_DISTANCE_LONG_CONFIG * VPR_CONFIG;
173         SetKnuckleDoubleTapDistance(distanceDefaultConfig_);
174         isDistanceConfig_ = true;
175     }
176 
177     switch (touchEvent->GetPointerAction()) {
178         case PointerEvent::POINTER_ACTION_CANCEL:
179         case PointerEvent::POINTER_ACTION_UP: {
180             HandlePointerActionUpEvent(touchEvent);
181             break;
182         }
183         case PointerEvent::POINTER_ACTION_MOVE: {
184             HandlePointerActionMoveEvent(touchEvent);
185             LONG_PRESS_EVENT_HANDLER->HandleFingerGestureMoveEvent(touchEvent);
186             break;
187         }
188         case PointerEvent::POINTER_ACTION_DOWN: {
189             HandlePointerActionDownEvent(touchEvent);
190             break;
191         }
192         default:
193             MMI_HILOGD("Unknown pointer action:%{public}d", touchEvent->GetPointerAction());
194             break;
195     }
196 #ifdef OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
197     HandleKnuckleGestureEvent(touchEvent);
198 #endif // OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
199 }
200 
HandlePointerActionDownEvent(const std::shared_ptr<PointerEvent> touchEvent)201 void KeyCommandHandler::HandlePointerActionDownEvent(const std::shared_ptr<PointerEvent> touchEvent)
202 {
203     CALL_DEBUG_ENTER;
204     CHKPV(touchEvent);
205     int32_t id = touchEvent->GetPointerId();
206     PointerEvent::PointerItem item;
207     touchEvent->GetPointerItem(id, item);
208     int32_t toolType = item.GetToolType();
209     MMI_HILOGD("Pointer tool type:%{public}d", toolType);
210     singleKnuckleGesture_.state = false;
211     doubleKnuckleGesture_.state = false;
212     switch (toolType) {
213 #ifdef OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
214         case PointerEvent::TOOL_TYPE_FINGER: {
215             HandleFingerGestureDownEvent(touchEvent);
216             if (CheckBundleName(touchEvent)) {
217                 LONG_PRESS_EVENT_HANDLER->HandleFingerGestureDownEvent(touchEvent);
218             }
219             break;
220         }
221         case PointerEvent::TOOL_TYPE_KNUCKLE: {
222             DfxHisysevent::ReportKnuckleClickEvent();
223             HandleKnuckleGestureDownEvent(touchEvent);
224             break;
225         }
226 #endif // OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
227         default: {
228             MMI_HILOGD("Current touch event tool type:%{public}d", toolType);
229             break;
230         }
231     }
232     CheckAndUpdateTappingCountAtDown(touchEvent);
233 }
234 
HandlePointerActionMoveEvent(const std::shared_ptr<PointerEvent> touchEvent)235 void KeyCommandHandler::HandlePointerActionMoveEvent(const std::shared_ptr<PointerEvent> touchEvent)
236 {
237     CALL_DEBUG_ENTER;
238     CHKPV(touchEvent);
239     int32_t id = touchEvent->GetPointerId();
240     PointerEvent::PointerItem item;
241     touchEvent->GetPointerItem(id, item);
242     if (!twoFingerGesture_.active) {
243         return;
244     }
245     if (twoFingerGesture_.timerId == -1) {
246         MMI_HILOGD("Two finger gesture timer id is -1");
247         return;
248     }
249     auto pos = std::find_if(std::begin(twoFingerGesture_.touches), std::end(twoFingerGesture_.touches),
250         [id](const auto& item) { return item.id == id; });
251     if (pos == std::end(twoFingerGesture_.touches)) {
252         return;
253     }
254     auto dx = std::abs(pos->x - item.GetDisplayX());
255     auto dy = std::abs(pos->y - item.GetDisplayY());
256     auto moveDistance = sqrt(pow(dx, 2) + pow(dy, 2));
257     if (moveDistance > ConvertVPToPX(TOUCH_MAX_THRESHOLD)) {
258 #ifdef OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
259         MMI_HILOGI("Finger movement distance greater than 20VP, defaultDistance:%{public}d, moveDistance:%{public}f",
260             ConvertVPToPX(TOUCH_MAX_THRESHOLD), moveDistance);
261         StopTwoFingerGesture();
262 #endif // OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
263     }
264 }
265 
HandlePointerActionUpEvent(const std::shared_ptr<PointerEvent> touchEvent)266 void KeyCommandHandler::HandlePointerActionUpEvent(const std::shared_ptr<PointerEvent> touchEvent)
267 {
268     CALL_DEBUG_ENTER;
269     CHKPV(touchEvent);
270     int32_t id = touchEvent->GetPointerId();
271     PointerEvent::PointerItem item;
272     touchEvent->GetPointerItem(id, item);
273     int32_t toolType = item.GetToolType();
274     switch (toolType) {
275 #ifdef OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
276         case PointerEvent::TOOL_TYPE_FINGER: {
277             HandleFingerGestureUpEvent(touchEvent);
278             LONG_PRESS_EVENT_HANDLER->HandleFingerGestureUpEvent(touchEvent);
279             break;
280         }
281         case PointerEvent::TOOL_TYPE_KNUCKLE: {
282             HandleKnuckleGestureUpEvent(touchEvent);
283             break;
284         }
285 #endif // OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
286         default: {
287             MMI_HILOGW("Current touch event tool type:%{public}d", toolType);
288             break;
289         }
290     }
291 }
292 #endif // OHOS_BUILD_ENABLE_TOUCH
293 
294 #ifdef OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
HandleFingerGestureDownEvent(const std::shared_ptr<PointerEvent> touchEvent)295 void KeyCommandHandler::HandleFingerGestureDownEvent(const std::shared_ptr<PointerEvent> touchEvent)
296 {
297     CALL_DEBUG_ENTER;
298     if (!twoFingerGesture_.active) {
299         MMI_HILOGD("Two finger gesture is not active");
300         return;
301     }
302     auto num = touchEvent->GetPointerIds().size();
303     if (num == TwoFingerGesture::MAX_TOUCH_NUM) {
304         StartTwoFingerGesture();
305     } else {
306         StopTwoFingerGesture();
307     }
308     if (num > 0 && num <= TwoFingerGesture::MAX_TOUCH_NUM) {
309         int32_t id = touchEvent->GetPointerId();
310         PointerEvent::PointerItem item;
311         touchEvent->GetPointerItem(id, item);
312         twoFingerGesture_.touches[num - 1].id = id;
313         twoFingerGesture_.touches[num - 1].x = item.GetDisplayX();
314         twoFingerGesture_.touches[num - 1].y = item.GetDisplayY();
315         twoFingerGesture_.touches[num - 1].downTime = item.GetDownTime();
316     }
317 }
318 
HandleFingerGestureUpEvent(const std::shared_ptr<PointerEvent> touchEvent)319 void KeyCommandHandler::HandleFingerGestureUpEvent(const std::shared_ptr<PointerEvent> touchEvent)
320 {
321     CALL_DEBUG_ENTER;
322     CHKPV(touchEvent);
323     if (!twoFingerGesture_.active) {
324         MMI_HILOGD("Two finger gesture is not active");
325         return;
326     }
327     StopTwoFingerGesture();
328 }
329 
HandleKnuckleGestureDownEvent(const std::shared_ptr<PointerEvent> touchEvent)330 void KeyCommandHandler::HandleKnuckleGestureDownEvent(const std::shared_ptr<PointerEvent> touchEvent)
331 {
332     CALL_DEBUG_ENTER;
333     CHKPV(touchEvent);
334     int32_t id = touchEvent->GetPointerId();
335     PointerEvent::PointerItem item;
336     touchEvent->GetPointerItem(id, item);
337     int64_t currentDownTime = item.GetDownTime();
338     if (!lastPointerDownTime_.empty()) {
339         int64_t firstDownTime = lastPointerDownTime_.begin()->second;
340         int64_t lastPointerDownTime = touchEvent->HasFlag(InputEvent::EVENT_FLAG_SIMULATE) ?
341             lastPointerDownTime_[SIMULATE_POINTER_ID] : firstDownTime;
342         int64_t diffTime = currentDownTime - lastPointerDownTime;
343         lastPointerDownTime_[id] = currentDownTime;
344         MMI_HILOGW("Size:%{public}zu, firstDownTime:%{public}" PRId64 ", "
345             "currentDownTime:%{public}" PRId64 ", diffTime:%{public}" PRId64,
346             lastPointerDownTime_.size(), firstDownTime, currentDownTime, diffTime);
347         if (diffTime > TWO_FINGERS_TIME_LIMIT) {
348             MMI_HILOGE("Invalid double knuckle event, pointerId:%{public}d", id);
349             return;
350         }
351     }
352 
353     lastPointerDownTime_[id] = currentDownTime;
354     auto items = touchEvent->GetAllPointerItems();
355     MMI_HILOGI("The itemsSize:%{public}zu", items.size());
356     for (const auto &item : items) {
357         if (item.GetToolType() != PointerEvent::TOOL_TYPE_KNUCKLE) {
358             MMI_HILOGW("Touch event tool type:%{public}d not knuckle", item.GetToolType());
359             return;
360         }
361     }
362     if (knuckleSwitch_.statusConfigValue) {
363         MMI_HILOGI("Knuckle switch closed");
364         return;
365     }
366     if (CheckInputMethodArea(touchEvent)) {
367         MMI_HILOGW("Event skipping inputmethod area");
368         return;
369     }
370     size_t pointercnt = touchEvent->GetPointerIds().size();
371     if (pointercnt == SINGLE_KNUCKLE_SIZE) {
372         SingleKnuckleGestureProcesser(touchEvent);
373         isDoubleClick_ = false;
374         knuckleCount_++;
375     } else if (pointercnt == DOUBLE_KNUCKLE_SIZE) {
376         DoubleKnuckleGestureProcesser(touchEvent);
377         isDoubleClick_ = true;
378     } else {
379         MMI_HILOGW("Other kunckle pointercnt not process, pointercnt:%{public}zu", pointercnt);
380     }
381 }
382 
HandleKnuckleGestureUpEvent(const std::shared_ptr<PointerEvent> touchEvent)383 void KeyCommandHandler::HandleKnuckleGestureUpEvent(const std::shared_ptr<PointerEvent> touchEvent)
384 {
385     CALL_DEBUG_ENTER;
386     CHKPV(touchEvent);
387     int32_t id = touchEvent->GetPointerId();
388     auto it = lastPointerDownTime_.find(id);
389     if (it != lastPointerDownTime_.end()) {
390         MMI_HILOGW("lastPointerDownTime_ has been erased, pointerId:%{public}d", id);
391         lastPointerDownTime_.erase(it);
392     }
393 
394     previousUpTime_ = touchEvent->GetActionTime();
395     size_t pointercnt = touchEvent->GetPointerIds().size();
396     if ((pointercnt == SINGLE_KNUCKLE_SIZE) && (!isDoubleClick_)) {
397         singleKnuckleGesture_.lastPointerUpTime = touchEvent->GetActionTime();
398     } else if (pointercnt == DOUBLE_KNUCKLE_SIZE) {
399         doubleKnuckleGesture_.lastPointerUpTime = touchEvent->GetActionTime();
400     } else {
401         MMI_HILOGW("Other kunckle pointercnt not process, pointercnt:%{public}zu", pointercnt);
402     }
403 }
404 
SingleKnuckleGestureProcesser(const std::shared_ptr<PointerEvent> touchEvent)405 void KeyCommandHandler::SingleKnuckleGestureProcesser(const std::shared_ptr<PointerEvent> touchEvent)
406 {
407     CALL_DEBUG_ENTER;
408     CHKPV(touchEvent);
409     singleKnuckleGesture_.state = false;
410     KnuckleGestureProcessor(touchEvent, singleKnuckleGesture_, KnuckleType::KNUCKLE_TYPE_SINGLE);
411 }
412 
DoubleKnuckleGestureProcesser(const std::shared_ptr<PointerEvent> touchEvent)413 void KeyCommandHandler::DoubleKnuckleGestureProcesser(const std::shared_ptr<PointerEvent> touchEvent)
414 {
415     CALL_DEBUG_ENTER;
416     CHKPV(touchEvent);
417     doubleKnuckleGesture_.state = false;
418     KnuckleGestureProcessor(touchEvent, doubleKnuckleGesture_, KnuckleType::KNUCKLE_TYPE_DOUBLE);
419 }
420 
KnuckleGestureProcessor(std::shared_ptr<PointerEvent> touchEvent,KnuckleGesture & knuckleGesture,KnuckleType type)421 void KeyCommandHandler::KnuckleGestureProcessor(std::shared_ptr<PointerEvent> touchEvent,
422     KnuckleGesture &knuckleGesture, KnuckleType type)
423 {
424     CALL_DEBUG_ENTER;
425     CHKPV(touchEvent);
426     if (knuckleGesture.lastPointerDownEvent == nullptr) {
427         MMI_HILOGI("Knuckle gesture first down Event");
428         knuckleGesture.lastPointerDownEvent = touchEvent;
429         UpdateKnuckleGestureInfo(touchEvent, knuckleGesture);
430         return;
431     }
432     int64_t intervalTime = touchEvent->GetActionTime() - knuckleGesture.lastPointerUpTime;
433     bool isTimeIntervalReady = intervalTime > 0 && intervalTime <= downToPrevUpTimeConfig_;
434     float downToPrevDownDistance = AbsDiff(knuckleGesture, touchEvent);
435     bool isDistanceReady = downToPrevDownDistance < downToPrevDownDistanceConfig_;
436     knuckleGesture.downToPrevUpTime = intervalTime;
437     knuckleGesture.doubleClickDistance = downToPrevDownDistance;
438     UpdateKnuckleGestureInfo(touchEvent, knuckleGesture);
439     if (isTimeIntervalReady && (type == KnuckleType::KNUCKLE_TYPE_DOUBLE || isDistanceReady)) {
440         MMI_HILOGI("Knuckle gesture start launch ability");
441         knuckleCount_ = 0;
442         if ((type == KnuckleType::KNUCKLE_TYPE_SINGLE && screenshotSwitch_.statusConfigValue) ||
443             (type == KnuckleType::KNUCKLE_TYPE_DOUBLE && recordSwitch_.statusConfigValue)) {
444             DfxHisysevent::ReportSingleKnuckleDoubleClickEvent(intervalTime, downToPrevDownDistance);
445             BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_FINGERSCENE, knuckleGesture.ability.bundleName);
446             LaunchAbility(knuckleGesture.ability, NO_DELAY);
447             BytraceAdapter::StopLaunchAbility();
448             if (knuckleGesture.ability.bundleName == SCREENRECORDER_BUNDLE_NAME) {
449                 DfxHisysevent::ReportScreenRecorderGesture(intervalTime);
450             }
451             ReportKnuckleScreenCapture(touchEvent);
452         }
453         knuckleGesture.state = true;
454     } else {
455         if (knuckleCount_ > KNUCKLE_KNOCKS) {
456             knuckleCount_ = 0;
457             MMI_HILOGW("Time ready:%{public}d, distance ready:%{public}d", isTimeIntervalReady, isDistanceReady);
458             if (!isTimeIntervalReady) {
459                 DfxHisysevent::ReportFailIfInvalidTime(touchEvent, intervalTime);
460             }
461             if (!isDistanceReady) {
462                 DfxHisysevent::ReportFailIfInvalidDistance(touchEvent, downToPrevDownDistance);
463             }
464         }
465     }
466     AdjustTimeIntervalConfigIfNeed(intervalTime);
467     AdjustDistanceConfigIfNeed(downToPrevDownDistance);
468 }
469 
SendNotSupportMsg(std::shared_ptr<PointerEvent> touchEvent)470 void KeyCommandHandler::SendNotSupportMsg(std::shared_ptr<PointerEvent> touchEvent)
471 {
472     CALL_DEBUG_ENTER;
473     CHKPV(touchEvent);
474     auto tempEvent = std::make_shared<PointerEvent>(*touchEvent);
475     std::list<PointerEvent::PointerItem> pointerItems = tempEvent->GetAllPointerItems();
476     tempEvent->RemoveAllPointerItems();
477     for (auto &pointerItem : pointerItems) {
478         pointerItem.SetPointerId(ANCO_KNUCKLE_POINTER_ID);
479         pointerItem.SetOriginPointerId(ANCO_KNUCKLE_POINTER_ID);
480         tempEvent->AddPointerItem(pointerItem);
481     }
482     tempEvent->SetPointerAction(PointerEvent::POINTER_ACTION_DOWN);
483     tempEvent->SetPointerId(ANCO_KNUCKLE_POINTER_ID);
484     tempEvent->SetAgentWindowId(tempEvent->GetTargetWindowId());
485     MMI_HILOGW("Event is %{public}s", tempEvent->ToString().c_str());
486     auto fd = WIN_MGR->GetClientFd(tempEvent);
487     auto udsServer = InputHandler->GetUDSServer();
488     CHKPV(udsServer);
489     NetPacket pkt(MmiMessageId::ON_POINTER_EVENT);
490     InputEventDataTransformation::Marshalling(tempEvent, pkt);
491 #ifdef OHOS_BUILD_ENABLE_SECURITY_COMPONENT
492     InputEventDataTransformation::MarshallingEnhanceData(tempEvent, pkt);
493 #endif // OHOS_BUILD_ENABLE_SECURITY_COMPONENT
494     udsServer->SendMsg(fd, pkt);
495 
496     tempEvent->SetPointerAction(PointerEvent::POINTER_ACTION_UP);
497     std::list<PointerEvent::PointerItem> tmpPointerItems = tempEvent->GetAllPointerItems();
498     tempEvent->RemoveAllPointerItems();
499     for (auto &pointerItem : tmpPointerItems) {
500         pointerItem.SetPressed(false);
501         tempEvent->AddPointerItem(pointerItem);
502     }
503     NetPacket pktUp(MmiMessageId::ON_POINTER_EVENT);
504     InputEventDataTransformation::Marshalling(tempEvent, pktUp);
505 #ifdef OHOS_BUILD_ENABLE_SECURITY_COMPONENT
506     InputEventDataTransformation::MarshallingEnhanceData(tempEvent, pktUp);
507 #endif // OHOS_BUILD_ENABLE_SECURITY_COMPONENT
508     udsServer->SendMsg(fd, pktUp);
509 }
510 
UpdateKnuckleGestureInfo(const std::shared_ptr<PointerEvent> touchEvent,KnuckleGesture & knuckleGesture)511 void KeyCommandHandler::UpdateKnuckleGestureInfo(const std::shared_ptr<PointerEvent> touchEvent,
512     KnuckleGesture &knuckleGesture)
513 {
514     int32_t id = touchEvent->GetPointerId();
515     PointerEvent::PointerItem item;
516     touchEvent->GetPointerItem(id, item);
517     knuckleGesture.lastDownPointer.x = item.GetDisplayX();
518     knuckleGesture.lastDownPointer.y = item.GetDisplayY();
519     knuckleGesture.lastDownPointer.id = touchEvent->GetId();
520 }
521 
AdjustTimeIntervalConfigIfNeed(int64_t intervalTime)522 void KeyCommandHandler::AdjustTimeIntervalConfigIfNeed(int64_t intervalTime)
523 {
524     CALL_DEBUG_ENTER;
525     int64_t newTimeConfig;
526     MMI_HILOGI("Down to prev up interval time:%{public}" PRId64 ",config time:%{public}" PRId64"",
527         intervalTime, downToPrevUpTimeConfig_);
528     if (downToPrevUpTimeConfig_ == DOUBLE_CLICK_INTERVAL_TIME_DEFAULT) {
529         if (intervalTime < DOUBLE_CLICK_INTERVAL_TIME_DEFAULT || intervalTime > DOUBLE_CLICK_INTERVAL_TIME_SLOW) {
530             return;
531         }
532         newTimeConfig = DOUBLE_CLICK_INTERVAL_TIME_SLOW;
533     } else if (downToPrevUpTimeConfig_ == DOUBLE_CLICK_INTERVAL_TIME_SLOW) {
534         if (intervalTime > DOUBLE_CLICK_INTERVAL_TIME_DEFAULT) {
535             return;
536         }
537         newTimeConfig = DOUBLE_CLICK_INTERVAL_TIME_DEFAULT;
538     } else {
539         return;
540     }
541     checkAdjustIntervalTimeCount_++;
542     if (checkAdjustIntervalTimeCount_ < MAX_TIME_FOR_ADJUST_CONFIG) {
543         return;
544     }
545     MMI_HILOGI("Adjust new double click interval time:%{public}" PRId64 "", newTimeConfig);
546     downToPrevUpTimeConfig_ = newTimeConfig;
547     checkAdjustIntervalTimeCount_ = 0;
548 }
549 
AdjustDistanceConfigIfNeed(float distance)550 void KeyCommandHandler::AdjustDistanceConfigIfNeed(float distance)
551 {
552     CALL_DEBUG_ENTER;
553     float newDistanceConfig;
554     MMI_HILOGI("Down to prev down distance:%{public}f, config distance:%{public}f",
555         distance, downToPrevDownDistanceConfig_);
556     if (IsEqual(downToPrevDownDistanceConfig_, distanceDefaultConfig_)) {
557         if (distance < distanceDefaultConfig_ || distance > distanceLongConfig_) {
558             return;
559         }
560         newDistanceConfig = distanceLongConfig_;
561     } else if (IsEqual(downToPrevDownDistanceConfig_, distanceLongConfig_)) {
562         if (distance > distanceDefaultConfig_) {
563             return;
564         }
565         newDistanceConfig = distanceDefaultConfig_;
566     } else {
567         return;
568     }
569     checkAdjustDistanceCount_++;
570     if (checkAdjustDistanceCount_ < MAX_TIME_FOR_ADJUST_CONFIG) {
571         return;
572     }
573     MMI_HILOGI("Adjust new double click distance:%{public}f", newDistanceConfig);
574     downToPrevDownDistanceConfig_ = newDistanceConfig;
575     checkAdjustDistanceCount_ = 0;
576 }
577 
ReportKnuckleScreenCapture(const std::shared_ptr<PointerEvent> touchEvent)578 void KeyCommandHandler::ReportKnuckleScreenCapture(const std::shared_ptr<PointerEvent> touchEvent)
579 {
580     CHKPV(touchEvent);
581     size_t pointercnt = touchEvent->GetPointerIds().size();
582     if (pointercnt == SINGLE_KNUCKLE_SIZE) {
583         DfxHisysevent::ReportScreenCaptureGesture();
584         return;
585     }
586     MMI_HILOGW("Current touch event pointercnt:%{public}zu", pointercnt);
587 }
588 
StartTwoFingerGesture()589 void KeyCommandHandler::StartTwoFingerGesture()
590 {
591     CALL_DEBUG_ENTER;
592     twoFingerGesture_.timerId = TimerMgr->AddTimer(twoFingerGesture_.abilityStartDelay, 1, [this]() {
593         twoFingerGesture_.timerId = -1;
594         if (!CheckTwoFingerGestureAction()) {
595             return;
596         }
597         twoFingerGesture_.ability.params["displayX1"] = std::to_string(twoFingerGesture_.touches[0].x);
598         twoFingerGesture_.ability.params["displayY1"] = std::to_string(twoFingerGesture_.touches[0].y);
599         twoFingerGesture_.ability.params["displayX2"] = std::to_string(twoFingerGesture_.touches[1].x);
600         twoFingerGesture_.ability.params["displayY2"] = std::to_string(twoFingerGesture_.touches[1].y);
601         MMI_HILOGI("Start launch ability immediately");
602         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_MULTI_FINGERS, twoFingerGesture_.ability.bundleName);
603         LaunchAbility(twoFingerGesture_.ability, twoFingerGesture_.abilityStartDelay);
604         BytraceAdapter::StopLaunchAbility();
605     });
606 }
607 
StopTwoFingerGesture()608 void KeyCommandHandler::StopTwoFingerGesture()
609 {
610     CALL_DEBUG_ENTER;
611     if (twoFingerGesture_.timerId != -1) {
612         TimerMgr->RemoveTimer(twoFingerGesture_.timerId);
613         twoFingerGesture_.timerId = -1;
614     }
615 }
616 
CheckTwoFingerGestureAction() const617 bool KeyCommandHandler::CheckTwoFingerGestureAction() const
618 {
619     if (!twoFingerGesture_.active) {
620         return false;
621     }
622 
623     auto firstFinger = twoFingerGesture_.touches[0];
624     auto secondFinger = twoFingerGesture_.touches[1];
625 
626     auto pressTimeInterval = fabs(firstFinger.downTime - secondFinger.downTime);
627     if (pressTimeInterval > TWO_FINGERS_TIME_LIMIT) {
628         return false;
629     }
630 
631 #ifdef OHOS_BUILD_ENABLE_TOUCH
632     auto devX = firstFinger.x - secondFinger.x;
633     auto devY = firstFinger.y - secondFinger.y;
634     auto distance = sqrt(pow(devX, 2) + pow(devY, 2));
635     if (distance < ConvertVPToPX(TWO_FINGERS_DISTANCE_LIMIT)) {
636         MMI_HILOGI("Two fingers distance:%{public}f too small", distance);
637         return false;
638     }
639 
640     auto displayInfo = WIN_MGR->GetDefaultDisplayInfo();
641     CHKPR(displayInfo, false);
642     auto leftLimit = ConvertVPToPX(TOUCH_LIFT_LIMIT);
643     auto rightLimit = displayInfo->width - ConvertVPToPX(TOUCH_RIGHT_LIMIT);
644     auto topLimit = ConvertVPToPX(TOUCH_TOP_LIMIT);
645     auto bottomLimit = displayInfo->height - ConvertVPToPX(TOUCH_BOTTOM_LIMIT);
646     if (firstFinger.x <= leftLimit || firstFinger.x >= rightLimit ||
647         firstFinger.y <= topLimit || firstFinger.y >= bottomLimit ||
648         secondFinger.x <= leftLimit || secondFinger.x >= rightLimit ||
649         secondFinger.y <= topLimit || secondFinger.y >= bottomLimit) {
650         MMI_HILOGI("Any finger out of region");
651         return false;
652     }
653 #endif // OHOS_BUILD_ENABLE_TOUCH
654 
655     return true;
656 }
657 #endif // OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
658 
659 #ifdef OHOS_BUILD_ENABLE_TOUCH
ConvertVPToPX(int32_t vp) const660 int32_t KeyCommandHandler::ConvertVPToPX(int32_t vp) const
661 {
662     if (vp <= 0) {
663         return 0;
664     }
665     auto displayInfo = WIN_MGR->GetDefaultDisplayInfo();
666     CHKPR(displayInfo, 0);
667     int32_t dpi = displayInfo->dpi;
668     if (dpi <= 0) {
669         return 0;
670     }
671     const int32_t base = 160;
672     return vp * (dpi / base);
673 }
674 #endif // OHOS_BUILD_ENABLE_TOUCH
675 
676 #ifdef OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
HandleKnuckleGestureEvent(std::shared_ptr<PointerEvent> touchEvent)677 void KeyCommandHandler::HandleKnuckleGestureEvent(std::shared_ptr<PointerEvent> touchEvent)
678 {
679     CALL_DEBUG_ENTER;
680     if (!CheckKnuckleCondition(touchEvent)) {
681         return;
682     }
683     CHKPV(touchEvent);
684     int32_t touchAction = touchEvent->GetPointerAction();
685     if (IsValidAction(touchAction)) {
686         switch (touchAction) {
687             case PointerEvent::POINTER_ACTION_CANCEL:
688             case PointerEvent::POINTER_ACTION_UP: {
689                 HandleKnuckleGestureTouchUp(touchEvent);
690                 break;
691             }
692             case PointerEvent::POINTER_ACTION_MOVE: {
693                 HandleKnuckleGestureTouchMove(touchEvent);
694                 break;
695             }
696             case PointerEvent::POINTER_ACTION_DOWN: {
697                 HandleKnuckleGestureTouchDown(touchEvent);
698                 break;
699             }
700             default:
701                 MMI_HILOGD("Unknown pointer action:%{public}d", touchAction);
702                 break;
703         }
704     }
705 }
706 
CheckKnuckleCondition(std::shared_ptr<PointerEvent> touchEvent)707 bool KeyCommandHandler::CheckKnuckleCondition(std::shared_ptr<PointerEvent> touchEvent)
708 {
709     CHKPF(touchEvent);
710     PointerEvent::PointerItem item;
711     touchEvent->GetPointerItem(touchEvent->GetPointerId(), item);
712     if (item.GetToolType() != PointerEvent::TOOL_TYPE_KNUCKLE ||
713         touchEvent->GetPointerIds().size() != SINGLE_KNUCKLE_SIZE || singleKnuckleGesture_.state) {
714         MMI_HILOGD("Touch tool type is:%{public}d", item.GetToolType());
715         ResetKnuckleGesture();
716         return false;
717     }
718     auto physicDisplayInfo = WIN_MGR->GetPhysicalDisplay(touchEvent->GetTargetDisplayId());
719     if (physicDisplayInfo != nullptr && physicDisplayInfo->direction != lastDirection_) {
720         lastDirection_ = physicDisplayInfo->direction;
721         if (touchEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_MOVE && !gesturePoints_.empty()) {
722             MMI_HILOGW("The screen has been rotated while knuckle is moving");
723             ResetKnuckleGesture();
724             return false;
725         }
726     }
727     if (knuckleSwitch_.statusConfigValue) {
728         if (touchEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_DOWN ||
729             touchEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_UP) {
730             MMI_HILOGI("Knuckle switch closed");
731         }
732         return false;
733     }
734     if (!screenshotSwitch_.statusConfigValue) {
735         if (touchEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_DOWN ||
736             touchEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_UP) {
737             MMI_HILOGI("Screenshot knuckle switch closed");
738         }
739         return false;
740     }
741     if (CheckInputMethodArea(touchEvent)) {
742         if (touchEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_DOWN ||
743             touchEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_UP) {
744             MMI_HILOGI("In input method area, skip");
745         }
746         return false;
747     }
748     return true;
749 }
750 
IsValidAction(int32_t action)751 bool KeyCommandHandler::IsValidAction(int32_t action)
752 {
753     CALL_DEBUG_ENTER;
754     if (action == PointerEvent::POINTER_ACTION_DOWN ||
755         ((action == PointerEvent::POINTER_ACTION_MOVE || action == PointerEvent::POINTER_ACTION_UP ||
756         action == PointerEvent::POINTER_ACTION_CANCEL) && !gesturePoints_.empty())) {
757         return true;
758     }
759     return false;
760 }
761 
CalcDrawCoordinate(const DisplayInfo & displayInfo,PointerEvent::PointerItem pointerItem)762 std::pair<int32_t, int32_t> KeyCommandHandler::CalcDrawCoordinate(const DisplayInfo& displayInfo,
763     PointerEvent::PointerItem pointerItem)
764 {
765     CALL_DEBUG_ENTER;
766     double physicalX = pointerItem.GetRawDisplayX();
767     double physicalY = pointerItem.GetRawDisplayY();
768     if (!displayInfo.transform.empty()) {
769         auto displayXY = WIN_MGR->TransformDisplayXY(displayInfo, physicalX, physicalY);
770         physicalX = displayXY.first;
771         physicalY = displayXY.second;
772     }
773     return {static_cast<int32_t>(physicalX), static_cast<int32_t>(physicalY)};
774 }
775 
HandleKnuckleGestureTouchDown(std::shared_ptr<PointerEvent> touchEvent)776 void KeyCommandHandler::HandleKnuckleGestureTouchDown(std::shared_ptr<PointerEvent> touchEvent)
777 {
778     CALL_DEBUG_ENTER;
779     CHKPV(touchEvent);
780     ResetKnuckleGesture();
781     isStartBase_ = false;
782     int32_t id = touchEvent->GetPointerId();
783     PointerEvent::PointerItem item;
784     touchEvent->GetPointerItem(id, item);
785     sessionKey_ = "Base" + std::to_string(item.GetDownTime());
786     auto displayInfo = WIN_MGR->GetPhysicalDisplay(touchEvent->GetTargetDisplayId());
787     CHKPV(displayInfo);
788     auto displayXY = CalcDrawCoordinate(*displayInfo, item);
789     gestureLastX_ = displayXY.first;
790     gestureLastY_ = displayXY.second;
791 
792     gesturePoints_.emplace_back(gestureLastX_);
793     gesturePoints_.emplace_back(gestureLastY_);
794     gestureTimeStamps_.emplace_back(touchEvent->GetActionTime());
795 }
796 
HandleKnuckleGestureTouchMove(std::shared_ptr<PointerEvent> touchEvent)797 void KeyCommandHandler::HandleKnuckleGestureTouchMove(std::shared_ptr<PointerEvent> touchEvent)
798 {
799     CALL_DEBUG_ENTER;
800     CHKPV(touchEvent);
801     PointerEvent::PointerItem item;
802     touchEvent->GetPointerItem(touchEvent->GetPointerId(), item);
803     auto displayInfo = WIN_MGR->GetPhysicalDisplay(touchEvent->GetTargetDisplayId());
804     CHKPV(displayInfo);
805     auto displayXY = CalcDrawCoordinate(*displayInfo, item);
806     float eventX = displayXY.first;
807     float eventY = displayXY.second;
808     float dx = std::abs(eventX - gestureLastX_);
809     float dy = std::abs(eventY - gestureLastY_);
810     if (dx >= MOVE_TOLERANCE || dy >= MOVE_TOLERANCE) {
811         gestureLastX_ = eventX;
812         gestureLastY_ = eventY;
813         gesturePoints_.emplace_back(gestureLastX_);
814         gesturePoints_.emplace_back(gestureLastY_);
815         gestureTimeStamps_.emplace_back(touchEvent->GetActionTime());
816         if (!isStartBase_ && IsMatchedAbility(gesturePoints_, gestureLastX_, gestureLastY_)) {
817             MMI_HILOGI("First time start aility, size:%{public}zu", gesturePoints_.size());
818             ProcessKnuckleGestureTouchUp(NotifyType::REGIONGESTURE);
819             isStartBase_ = true;
820         }
821         if (!isGesturing_) {
822             gestureTrackLength_ += sqrt(dx * dx + dy * dy);
823             if (gestureTrackLength_ > MIN_GESTURE_STROKE_LENGTH) {
824                 isGesturing_ = true;
825             }
826         }
827         if (isGesturing_ && !isLetterGesturing_) {
828             auto GetBoundingSquareness = GESTURESENSE_WRAPPER->getBoundingSquareness_;
829             CHKPV(GetBoundingSquareness);
830             auto boundingSquareness = GetBoundingSquareness(gesturePoints_);
831             if (boundingSquareness > MIN_LETTER_GESTURE_SQUARENESS) {
832                 isLetterGesturing_ = true;
833             }
834         }
835     }
836 }
837 
HandleKnuckleGestureTouchUp(std::shared_ptr<PointerEvent> touchEvent)838 void KeyCommandHandler::HandleKnuckleGestureTouchUp(std::shared_ptr<PointerEvent> touchEvent)
839 {
840     CALL_DEBUG_ENTER;
841     CHKPV(touchEvent);
842     auto touchUp = GESTURESENSE_WRAPPER->touchUp_;
843     CHKPV(touchUp);
844     MMI_HILOGI("Knuckle gesturePoints size:%{public}zu, isGesturing:%{public}d, isLetterGesturing:%{public}d",
845         gesturePoints_.size(), isGesturing_, isLetterGesturing_);
846     NotifyType notifyType = static_cast<NotifyType>(touchUp(gesturePoints_, gestureTimeStamps_,
847         isGesturing_, isLetterGesturing_));
848     switch (notifyType) {
849         case NotifyType::REGIONGESTURE: {
850             ProcessKnuckleGestureTouchUp(notifyType);
851             drawOSuccTimestamp_ = touchEvent->GetActionTime();
852             ReportRegionGesture();
853             break;
854         }
855         case NotifyType::LETTERGESTURE: {
856             ProcessKnuckleGestureTouchUp(notifyType);
857             drawOFailTimestamp_ = touchEvent->GetActionTime();
858             ReportLetterGesture();
859             break;
860         }
861         default: {
862             MMI_HILOGW("Not a region gesture or letter gesture, notifyType:%{public}d", notifyType);
863             drawOFailTimestamp_ = touchEvent->GetActionTime();
864             ReportIfNeed();
865             break;
866         }
867     }
868     ResetKnuckleGesture();
869 }
870 
ProcessKnuckleGestureTouchUp(NotifyType type)871 void KeyCommandHandler::ProcessKnuckleGestureTouchUp(NotifyType type)
872 {
873     Ability ability;
874     ability.abilityType = EXTENSION_ABILITY;
875     if (type == NotifyType::REGIONGESTURE) {
876         ability.abilityName = WAKEUP_ABILITY_NAME;
877         ability.bundleName = AIBASE_BUNDLE_NAME;
878         ability.params.emplace(std::make_pair("shot_type", "smart-shot"));
879         MMI_HILOGI("The isStartBase_:%{public}d, sessionKey_:%{public}s", isStartBase_, sessionKey_.c_str());
880         if (!isStartBase_) {
881             ability.params.emplace(std::make_pair("fingerPath", ""));
882             ability.params.emplace(std::make_pair("launch_type", "knuckle_gesture_pre"));
883         } else {
884             ability.params.emplace(std::make_pair("fingerPath", GesturePointsToStr()));
885             ability.params.emplace(std::make_pair("launch_type", "knuckle_gesture"));
886         }
887         ability.params.emplace(std::make_pair("session_id", sessionKey_));
888     } else if (type == NotifyType::LETTERGESTURE) {
889         ability.abilityName = SCREENSHOT_ABILITY_NAME;
890         ability.bundleName = SCREENSHOT_BUNDLE_NAME;
891         ability.params.emplace(std::make_pair("shot_type", "scroll-shot"));
892         ability.params.emplace(std::make_pair("trigger_type", "knuckle"));
893     }
894     LaunchAbility(ability, NO_DELAY);
895 }
896 
ResetKnuckleGesture()897 void KeyCommandHandler::ResetKnuckleGesture()
898 {
899     gestureLastX_ = 0.0f;
900     gestureLastY_ = 0.0f;
901     isGesturing_ = false;
902     isLetterGesturing_ = false;
903     gestureTrackLength_ = 0.0f;
904     gesturePoints_.clear();
905     gestureTimeStamps_.clear();
906 }
907 
GesturePointsToStr() const908 std::string KeyCommandHandler::GesturePointsToStr() const
909 {
910     int32_t count = static_cast<int32_t>(gesturePoints_.size());
911     if (count % EVEN_NUMBER != 0 || count == 0) {
912         MMI_HILOGE("Invalid gesturePoints_ size");
913         return {};
914     }
915     cJSON *jsonArray = cJSON_CreateArray();
916     for (int32_t i = 0; i < count; i += EVEN_NUMBER) {
917         cJSON *jsonData = cJSON_CreateObject();
918         cJSON_AddItemToObject(jsonData, "x", cJSON_CreateNumber(gesturePoints_[i]));
919         cJSON_AddItemToObject(jsonData, "y", cJSON_CreateNumber(gesturePoints_[i + 1]));
920         cJSON_AddItemToArray(jsonArray, jsonData);
921     }
922     char *jsonString = cJSON_Print(jsonArray);
923     std::string result = std::string(jsonString);
924     cJSON_Delete(jsonArray);
925     cJSON_free(jsonString);
926     return result;
927 }
928 
ReportIfNeed()929 void KeyCommandHandler::ReportIfNeed()
930 {
931     if (!isGesturing_) {
932         return;
933     }
934     DfxHisysevent::ReportKnuckleGestureFaildTimes();
935     DfxHisysevent::ReportKnuckleGestureTrackLength(gestureTrackLength_);
936     DfxHisysevent::ReportKnuckleGestureTrackTime(gestureTimeStamps_);
937     if (isLastGestureSucceed_) {
938         DfxHisysevent::ReportKnuckleGestureFromSuccessToFailTime(drawOFailTimestamp_ - drawOSuccTimestamp_);
939     }
940     isLastGestureSucceed_ = false;
941 }
942 
ReportRegionGesture()943 void KeyCommandHandler::ReportRegionGesture()
944 {
945     DfxHisysevent::ReportSmartShotSuccTimes();
946     ReportGestureInfo();
947 }
948 
ReportLetterGesture()949 void KeyCommandHandler::ReportLetterGesture()
950 {
951     DfxHisysevent::ReportKnuckleDrawSSuccessTimes();
952     ReportGestureInfo();
953 }
954 
ReportGestureInfo()955 void KeyCommandHandler::ReportGestureInfo()
956 {
957     DfxHisysevent::ReportKnuckleGestureTrackLength(gestureTrackLength_);
958     DfxHisysevent::ReportKnuckleGestureTrackTime(gestureTimeStamps_);
959     if (!isLastGestureSucceed_) {
960         DfxHisysevent::ReportKnuckleGestureFromFailToSuccessTime(drawOSuccTimestamp_ - drawOFailTimestamp_);
961     }
962     isLastGestureSucceed_ = true;
963 }
964 
IsMatchedAbility(std::vector<float> gesturePoints,float gestureLastX,float gestureLastY)965 bool KeyCommandHandler::IsMatchedAbility(std::vector<float> gesturePoints,
966     float gestureLastX, float gestureLastY)
967 {
968     if (gesturePoints.size() < POINTER_NUMBER) {
969         MMI_HILOGI("The gesturePoints_ is empty");
970         return false;
971     }
972     float gestureFirstX = gesturePoints[0];
973     float gestureFirstY = gesturePoints[1];
974     float distance = std::min(std::abs(gestureLastX - gestureFirstX), std::abs(gestureLastY - gestureFirstY));
975     return distance >= MIN_START_GESTURE;
976 }
977 #endif // OHOS_BUILD_ENABLE_GESTURESENSE_WRAPPER
978 
ParseConfig()979 bool KeyCommandHandler::ParseConfig()
980 {
981     const std::string defaultConfig { "/system/etc/multimodalinput/ability_launch_config.json" };
982     const char configName[] { "/etc/multimodalinput/ability_launch_config.json" };
983     char buf[MAX_PATH_LEN] {};
984 
985     char *filePath = ::GetOneCfgFile(configName, buf, sizeof(buf));
986     if (filePath == nullptr || filePath[0] == '\0' || strlen(filePath) > MAX_PATH_LEN) {
987         MMI_HILOGD("Can not get customization config file");
988         return ParseJson(defaultConfig);
989     }
990     std::string customConfig = filePath;
991     MMI_HILOGD("The configuration file path:%{private}s", customConfig.c_str());
992     return ParseJson(customConfig) || ParseJson(defaultConfig);
993 }
994 
ParseExcludeConfig()995 bool KeyCommandHandler::ParseExcludeConfig()
996 {
997     const std::string defaultConfig { "/system/etc/multimodalinput/exclude_keys_config.json" };
998     const char configName[] { "/etc/multimodalinput/exclude_keys_config.json" };
999     char buf[MAX_PATH_LEN] {};
1000 
1001     char *filePath = ::GetOneCfgFile(configName, buf, sizeof(buf));
1002     if (filePath == nullptr || filePath[0] == '\0' || strlen(filePath) > MAX_PATH_LEN) {
1003         MMI_HILOGD("Can not get customization exclude_keys_config.json file");
1004         return ParseExcludeJson(defaultConfig);
1005     }
1006     std::string customConfig = filePath;
1007     MMI_HILOGD("The exclude_keys_config.json file path:%s", customConfig.c_str());
1008     return ParseExcludeJson(customConfig) || ParseExcludeJson(defaultConfig);
1009 }
1010 
ParseRepeatKeyMaxCount()1011 void KeyCommandHandler::ParseRepeatKeyMaxCount()
1012 {
1013     if (repeatKeys_.empty()) {
1014         maxCount_ = 0;
1015     }
1016     int32_t tempCount = 0;
1017     int32_t tempDelay = 0;
1018     for (RepeatKey& item : repeatKeys_) {
1019         if (item.times > tempCount) {
1020             tempCount = item.times;
1021         }
1022         if (item.delay > tempDelay) {
1023             tempDelay = item.delay;
1024         }
1025         if (item.ability.bundleName == WALLET_BUNDLE_NAME) {
1026             walletLaunchDelayTimes_ = item.delay;
1027         }
1028     }
1029     maxCount_ = tempCount;
1030     intervalTime_ = tempDelay;
1031 }
1032 
CheckSpecialRepeatKey(RepeatKey & item,const std::shared_ptr<KeyEvent> keyEvent)1033 bool KeyCommandHandler::CheckSpecialRepeatKey(RepeatKey& item, const std::shared_ptr<KeyEvent> keyEvent)
1034 {
1035     if (item.keyCode != keyEvent->GetKeyCode()) {
1036         return false;
1037     }
1038     if (item.keyCode != KeyEvent::KEYCODE_VOLUME_DOWN) {
1039         return false;
1040     }
1041     std::string bundleName = item.ability.bundleName;
1042     std::string matchName = ".camera";
1043     if (bundleName.find(matchName) == std::string::npos) {
1044         return false;
1045     }
1046     std::string screenStatus = DISPLAY_MONITOR->GetScreenStatus();
1047     bool isScreenLocked = DISPLAY_MONITOR->GetScreenLocked();
1048     if (WIN_MGR->JudgeCaramaInFore() &&
1049         (screenStatus != EventFwk::CommonEventSupport::COMMON_EVENT_SCREEN_OFF && isScreenLocked)) {
1050             return true;
1051     }
1052     auto callState = DEVICE_MONITOR->GetCallState();
1053     if (callState == StateType::CALL_STATUS_ACTIVE) {
1054         return true;
1055     }
1056     if ((screenStatus == EventFwk::CommonEventSupport::COMMON_EVENT_SCREEN_OFF || isScreenLocked) &&
1057         !IsMusicActivate()) {
1058         return true;
1059     }
1060     MMI_HILOGI("ScreenStatus:%{public}s, isScreenLocked:%{public}d", screenStatus.c_str(), isScreenLocked);
1061     if (screenStatus == EventFwk::CommonEventSupport::COMMON_EVENT_SCREEN_OFF || isScreenLocked) {
1062         return false;
1063     }
1064     return true;
1065 }
1066 
ParseJson(const std::string & configFile)1067 bool KeyCommandHandler::ParseJson(const std::string &configFile)
1068 {
1069     CALL_DEBUG_ENTER;
1070     std::string jsonStr = ReadJsonFile(configFile);
1071     if (jsonStr.empty()) {
1072         MMI_HILOGE("Read configFile failed");
1073         return false;
1074     }
1075     JsonParser parser;
1076     parser.json_ = cJSON_Parse(jsonStr.c_str());
1077     if (parser.json_ == nullptr) {
1078         MMI_HILOGE("cJSON_Parse failed");
1079         return false;
1080     }
1081     if (!cJSON_IsObject(parser.json_)) {
1082         MMI_HILOGE("Parser.json_ is not object");
1083         return false;
1084     }
1085 
1086     bool isParseShortKeys = ParseShortcutKeys(parser, shortcutKeys_, businessIds_);
1087     bool isParseSequences = ParseSequences(parser, sequences_);
1088     bool isParseTwoFingerGesture = ParseTwoFingerGesture(parser, twoFingerGesture_);
1089     bool isParseSingleKnuckleGesture = IsParseKnuckleGesture(parser, SINGLE_KNUCKLE_ABILITY, singleKnuckleGesture_);
1090     bool isParseDoubleKnuckleGesture = IsParseKnuckleGesture(parser, DOUBLE_KNUCKLE_ABILITY, doubleKnuckleGesture_);
1091     bool isParseMultiFingersTap = ParseMultiFingersTap(parser, TOUCHPAD_TRIP_TAP_ABILITY, threeFingersTap_);
1092     bool isParseRepeatKeys = ParseRepeatKeys(parser, repeatKeys_, repeatKeyMaxTimes_);
1093     knuckleSwitch_.statusConfig = SETTING_KNUCKLE_SWITCH;
1094     screenshotSwitch_.statusConfig = SETTING_KNUCKLE_SWITCH;
1095     screenshotSwitch_.statusConfigValue = true;
1096     recordSwitch_.statusConfig = SETTING_KNUCKLE_SWITCH;
1097     recordSwitch_.statusConfigValue = true;
1098     if (!isParseShortKeys && !isParseSequences && !isParseTwoFingerGesture && !isParseSingleKnuckleGesture &&
1099         !isParseDoubleKnuckleGesture && !isParseMultiFingersTap && !isParseRepeatKeys) {
1100         MMI_HILOGE("Parse configFile failed");
1101         return false;
1102     }
1103 
1104     Print();
1105     PrintSeq();
1106     return true;
1107 }
1108 
ParseExcludeJson(const std::string & configFile)1109 bool KeyCommandHandler::ParseExcludeJson(const std::string &configFile)
1110 {
1111     CALL_DEBUG_ENTER;
1112     std::string jsonStr = ReadJsonFile(configFile);
1113     if (jsonStr.empty()) {
1114         MMI_HILOGE("Read excludeKey configFile failed");
1115         return false;
1116     }
1117     JsonParser parser;
1118     parser.json_ = cJSON_Parse(jsonStr.c_str());
1119     if (!cJSON_IsObject(parser.json_)) {
1120         MMI_HILOGE("Parser.json_ of excludeKey is not object");
1121         return false;
1122     }
1123     bool isParseExcludeKeys = ParseExcludeKeys(parser, excludeKeys_);
1124     if (!isParseExcludeKeys) {
1125         MMI_HILOGE("Parse ExcludeKeys configFile failed");
1126         return false;
1127     }
1128     PrintExcludeKeys();
1129     return true;
1130 }
1131 
Print()1132 void KeyCommandHandler::Print()
1133 {
1134     MMI_HILOGI("ShortcutKey count:%{public}zu", shortcutKeys_.size());
1135     int32_t row = 0;
1136     for (const auto &item : shortcutKeys_) {
1137         MMI_HILOGI("The row:%{public}d", row++);
1138         auto &shortcutKey = item.second;
1139         for (const auto &prekey : shortcutKey.preKeys) {
1140             MMI_HILOGI("The preKey:%d", prekey);
1141         }
1142         MMI_HILOGI("The finalKey:%d, keyDownDuration:%{public}d, triggerType:%{public}d,"
1143                    " bundleName:%{public}s, abilityName:%{public}s", shortcutKey.finalKey,
1144                    shortcutKey.keyDownDuration, shortcutKey.triggerType,
1145                    shortcutKey.ability.bundleName.c_str(), shortcutKey.ability.abilityName.c_str());
1146     }
1147 }
1148 
PrintExcludeKeys()1149 void KeyCommandHandler::PrintExcludeKeys()
1150 {
1151     size_t keysSize = excludeKeys_.size();
1152     for (size_t i = 0; i < keysSize; i++) {
1153         MMI_HILOGD("keyCode:%d, keyAction:%{public}d, delay:%{public}" PRId64,
1154                    excludeKeys_[i].keyCode, excludeKeys_[i].keyAction, excludeKeys_[i].delay);
1155     }
1156 }
1157 
PrintSeq()1158 void KeyCommandHandler::PrintSeq()
1159 {
1160     MMI_HILOGI("Sequences count:%{public}zu", sequences_.size());
1161     int32_t row = 0;
1162     for (const auto &item : sequences_) {
1163         MMI_HILOGI("The row:%{public}d", row++);
1164         for (const auto& sequenceKey : item.sequenceKeys) {
1165             MMI_HILOGI("The keyCode:%d, keyAction:%{public}d, delay:%{public}" PRId64,
1166                        sequenceKey.keyCode, sequenceKey.keyAction, sequenceKey.delay);
1167         }
1168         MMI_HILOGI("Ability bundleName:%{public}s, abilityName:%{public}s",
1169                    item.ability.bundleName.c_str(), item.ability.abilityName.c_str());
1170     }
1171 }
1172 
IsExcludeKey(const std::shared_ptr<KeyEvent> key)1173 bool KeyCommandHandler::IsExcludeKey(const std::shared_ptr<KeyEvent> key)
1174 {
1175     size_t keysSize = excludeKeys_.size();
1176     for (size_t i = 0; i < keysSize; i++) {
1177         if (key->GetKeyCode() == excludeKeys_[i].keyCode) {
1178             if (key->GetKeyAction() == excludeKeys_[i].keyAction) {
1179                 return true;
1180             }
1181         }
1182     }
1183     return false;
1184 }
1185 
IsEnableCombineKey(const std::shared_ptr<KeyEvent> key)1186 bool KeyCommandHandler::IsEnableCombineKey(const std::shared_ptr<KeyEvent> key)
1187 {
1188     CHKPF(key);
1189     if (enableCombineKey_) {
1190         return true;
1191     }
1192 
1193     if (!isParseExcludeConfig_) {
1194         if (!ParseExcludeConfig()) {
1195             DfxHisysevent::ReportFailHandleKey("IsEnableCombineKey", key->GetKeyCode(),
1196                 DfxHisysevent::KEY_ERROR_CODE::FAILED_PARSE_CONFIG);
1197             MMI_HILOGE("Parse Exclude configFile failed");
1198             return false;
1199         }
1200         isParseExcludeConfig_ = true;
1201     }
1202 
1203     if (IsExcludeKey(key)) {
1204         if (EventLogHelper::IsBetaVersion() && !key->HasFlag(InputEvent::EVENT_FLAG_PRIVACY_MODE)) {
1205             MMI_HILOGD("ExcludekeyCode:%{private}d,ExcludekeyAction:%{public}d",
1206                 key->GetKeyCode(), key->GetKeyAction());
1207         } else {
1208             MMI_HILOGD("ExcludekeyCode:%d, ExcludekeyAction:%{public}d", key->GetKeyCode(), key->GetKeyAction());
1209         }
1210         auto items = key->GetKeyItems();
1211         MMI_HILOGI("KeyItemsSize:%{public}zu", items.size());
1212         if (items.size() != 1) {
1213             return enableCombineKey_;
1214         }
1215         return true;
1216     }
1217     if (key->GetKeyCode() == KeyEvent::KEYCODE_L) {
1218         for (const auto &item : key->GetKeyItems()) {
1219             int32_t keyCode = item.GetKeyCode();
1220             if (keyCode != KeyEvent::KEYCODE_L && keyCode != KeyEvent::KEYCODE_META_LEFT &&
1221                 keyCode != KeyEvent::KEYCODE_META_RIGHT) {
1222                 MMI_HILOGI("GetKeyCode:%d", keyCode);
1223                 return enableCombineKey_;
1224             }
1225         }
1226         return true;
1227     }
1228     return enableCombineKey_;
1229 }
1230 
EnableCombineKey(bool enable)1231 int32_t KeyCommandHandler::EnableCombineKey(bool enable)
1232 {
1233     enableCombineKey_ = enable;
1234     MMI_HILOGI("Enable combineKey is successful in keyCommand handler, enable:%{public}d", enable);
1235     return RET_OK;
1236 }
1237 
ParseStatusConfigObserver()1238 void KeyCommandHandler::ParseStatusConfigObserver()
1239 {
1240     CALL_DEBUG_ENTER;
1241     for (Sequence& item : sequences_) {
1242         if (item.statusConfig.empty()) {
1243             continue;
1244         }
1245         CreateStatusConfigObserver<Sequence>(item);
1246     }
1247 
1248     for (auto& item : shortcutKeys_) {
1249         ShortcutKey &shortcutKey = item.second;
1250         if (shortcutKey.statusConfig.empty()) {
1251             continue;
1252         }
1253         CreateStatusConfigObserver<ShortcutKey>(shortcutKey);
1254     }
1255 }
1256 
1257 template <class T>
CreateStatusConfigObserver(T & item)1258 void KeyCommandHandler::CreateStatusConfigObserver(T& item)
1259 {
1260     CALL_DEBUG_ENTER;
1261     SettingObserver::UpdateFunc updateFunc = [weak = weak_from_this(), &item](const std::string& key) {
1262         auto ptr = weak.lock();
1263         if (ptr == nullptr) {
1264             return;
1265         }
1266         bool statusValue = true;
1267         auto ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID)
1268             .GetBoolValue(key, statusValue);
1269         if (ret != RET_OK) {
1270             MMI_HILOGE("Get value from setting date fail");
1271             return;
1272         }
1273         MMI_HILOGI("Config changed key:%s, value:%{public}d", key.c_str(), statusValue);
1274         item.statusConfigValue = statusValue;
1275         ptr->OnKunckleSwitchStatusChange(item.statusConfig);
1276     };
1277     sptr<SettingObserver> statusObserver = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID)
1278         .CreateObserver(item.statusConfig, updateFunc);
1279     ErrCode ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).RegisterObserver(statusObserver);
1280     if (ret != ERR_OK) {
1281         MMI_HILOGE("Register setting observer failed, ret:%{public}d", ret);
1282         statusObserver = nullptr;
1283     }
1284     bool configVlaue = true;
1285     ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID)
1286         .GetBoolValue(item.statusConfig, configVlaue);
1287     if (ret != RET_OK) {
1288         MMI_HILOGE("Get value from setting date fail");
1289         return;
1290     }
1291     MMI_HILOGI("Get value success key:%s, value:%{public}d", item.statusConfig.c_str(), configVlaue);
1292     item.statusConfigValue = configVlaue;
1293 }
1294 
RegisterKnuckleSwitchByUserId(int32_t userId)1295 int32_t KeyCommandHandler::RegisterKnuckleSwitchByUserId(int32_t userId)
1296 {
1297     CALL_DEBUG_ENTER;
1298     currentUserId_ = userId;
1299     CreateKnuckleConfigObserver(screenshotSwitch_);
1300     CreateKnuckleConfigObserver(recordSwitch_);
1301     return RET_OK;
1302 }
1303 
1304 template <class T>
CreateKnuckleConfigObserver(T & item)1305 void KeyCommandHandler::CreateKnuckleConfigObserver(T& item)
1306 {
1307     CALL_DEBUG_ENTER;
1308     char buf[DEFAULT_BUFFER_LENGTH] {};
1309     if (sprintf_s(buf, sizeof(buf), SECURE_SETTING_URI_PROXY.c_str(), currentUserId_) < 0) {
1310         MMI_HILOGE("Failed to format URI");
1311         return;
1312     }
1313     SettingObserver::UpdateFunc updateFunc = [weak = weak_from_this(), &item, buf](const std::string& key) {
1314         auto ptr = weak.lock();
1315         if (ptr == nullptr) {
1316             return;
1317         }
1318         bool statusValue = true;
1319         ErrCode ret = RET_ERR;
1320         MMI_HILOGI("The statusConfig:%s", item.statusConfig.c_str());
1321         ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).GetBoolValue(key, statusValue,
1322             std::string(buf));
1323         if (ret != RET_OK) {
1324             MMI_HILOGE("Get value from setting data fail");
1325             item.statusConfigValue = true;
1326             return;
1327         }
1328         MMI_HILOGI("Config changed key:%s, value:%{public}d", key.c_str(), statusValue);
1329         item.statusConfigValue = statusValue;
1330         ptr->OnKunckleSwitchStatusChange(item.statusConfig);
1331     };
1332     sptr<SettingObserver> statusObserver = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID)
1333         .CreateObserver(item.statusConfig, updateFunc);
1334     ErrCode ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).RegisterObserver(statusObserver,
1335         std::string(buf));
1336     if (ret != ERR_OK) {
1337         MMI_HILOGE("Register setting observer failed, ret:%{public}d", ret);
1338         statusObserver = nullptr;
1339     }
1340     bool configValue = true;
1341     ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID)
1342         .GetBoolValue(item.statusConfig, configValue, std::string(buf));
1343     if (ret != RET_OK) {
1344         MMI_HILOGE("Get value from setting data fail");
1345         item.statusConfigValue = true;
1346         return;
1347     }
1348     MMI_HILOGI("Get value success key:%s, value:%{public}d", item.statusConfig.c_str(), configValue);
1349     item.statusConfigValue = configValue;
1350 }
1351 
CreateKeyEvent(int32_t keyCode,int32_t keyAction,bool isPressed)1352 std::shared_ptr<KeyEvent> KeyCommandHandler::CreateKeyEvent(int32_t keyCode, int32_t keyAction, bool isPressed)
1353 {
1354     CALL_DEBUG_ENTER;
1355     std::shared_ptr<KeyEvent> keyEvent = KeyEvent::Create();
1356     CHKPP(keyEvent);
1357     KeyEvent::KeyItem item;
1358     item.SetKeyCode(keyCode);
1359     item.SetPressed(isPressed);
1360     keyEvent->SetKeyCode(keyCode);
1361     keyEvent->SetKeyAction(keyAction);
1362     keyEvent->AddPressedKeyItems(item);
1363     return keyEvent;
1364 }
1365 
PreHandleEvent(const std::shared_ptr<KeyEvent> key)1366 bool KeyCommandHandler::PreHandleEvent(const std::shared_ptr<KeyEvent> key)
1367 {
1368     CHKPF(key);
1369     if (EventLogHelper::IsBetaVersion() && !key->HasFlag(InputEvent::EVENT_FLAG_PRIVACY_MODE)) {
1370         MMI_HILOGD("KeyEvent occured. keyCode:%{public}d, keyAction:%{public}d",
1371             key->GetKeyCode(), key->GetKeyAction());
1372     } else {
1373         MMI_HILOGD("KeyEvent occured. keyCode:%d, keyAction:%{public}d", key->GetKeyCode(), key->GetKeyAction());
1374     }
1375     if (key->GetKeyCode() == KeyEvent::KEYCODE_F1) {
1376         DfxHisysevent::ReportKeyEvent("screen on");
1377     }
1378     if (!IsEnableCombineKey(key)) {
1379         MMI_HILOGI("Combine key is taken over in key command");
1380         return false;
1381     }
1382     if (!isParseConfig_) {
1383         if (!ParseConfig()) {
1384             MMI_HILOGE("Parse configFile failed");
1385             DfxHisysevent::ReportFailHandleKey("PreHandleEvent", key->GetKeyCode(),
1386                 DfxHisysevent::KEY_ERROR_CODE::FAILED_PARSE_CONFIG);
1387             return false;
1388         }
1389         isParseConfig_ = true;
1390     }
1391     if (!isParseLongPressConfig_) {
1392         if (!ParseLongPressConfig()) {
1393             MMI_HILOGE("Parse long press configFile failed");
1394             DfxHisysevent::ReportFailHandleKey("PreHandleEvent", key->GetKeyCode(),
1395                 DfxHisysevent::KEY_ERROR_CODE::FAILED_PARSE_CONFIG);
1396         }
1397         isParseLongPressConfig_ = true;
1398     }
1399     if (!isParseMaxCount_) {
1400         ParseRepeatKeyMaxCount();
1401         isParseMaxCount_ = true;
1402     }
1403     if (key->GetKeyCode() == KeyEvent::KEYCODE_VOLUME_DOWN || key->GetKeyCode() == KeyEvent::KEYCODE_VOLUME_UP) {
1404         lastVolumeDownActionTime_ = key->GetActionTime();
1405     }
1406     return true;
1407 }
1408 
PreHandleEvent()1409 bool KeyCommandHandler::PreHandleEvent()
1410 {
1411     CALL_INFO_TRACE;
1412     if (!isParseConfig_) {
1413         if (!ParseConfig()) {
1414             MMI_HILOGE("Parse configFile failed");
1415             return false;
1416         }
1417         isParseConfig_ = true;
1418     }
1419     if (!isParseLongPressConfig_) {
1420         if (!ParseLongPressConfig()) {
1421             MMI_HILOGE("Parse long press configFile failed");
1422         }
1423         isParseLongPressConfig_ = true;
1424     }
1425     if (!isParseMaxCount_) {
1426         ParseRepeatKeyMaxCount();
1427         isParseMaxCount_ = true;
1428     }
1429     return true;
1430 }
1431 
HandleEvent(const std::shared_ptr<KeyEvent> key)1432 bool KeyCommandHandler::HandleEvent(const std::shared_ptr<KeyEvent> key)
1433 {
1434     CALL_DEBUG_ENTER;
1435     CHKPF(key);
1436     if (!PreHandleEvent(key)) {
1437         return false;
1438     }
1439 
1440     if (STYLUS_HANDLER->HandleStylusKey(key)) {
1441         DfxHisysevent::ReportKeyEvent("stylus");
1442         return true;
1443     }
1444 
1445     bool shortKeysHandleRet = HandleShortKeys(key);
1446     if (key->GetKeyCode() == KeyEvent::KEYCODE_POWER && key->GetKeyAction() == KeyEvent::KEY_ACTION_UP) {
1447         powerUpTime_ = key->GetActionTime();
1448     }
1449     if (key->GetKeyCode() == KeyEvent::KEYCODE_POWER && key->GetKeyAction() == KeyEvent::KEY_ACTION_DOWN) {
1450         if ((key->GetActionTime() - powerUpTime_) > POWER_ACTION_INTERVAL * FREQUENCY &&
1451             (key->GetActionTime() - sosLaunchTime_) > SOS_WAIT_TIME * FREQUENCY) {
1452                 MMI_HILOGI("Set isFreezePowerKey as false");
1453                 isFreezePowerKey_ = false;
1454             }
1455     }
1456     if (key->GetKeyCode() == KeyEvent::KEYCODE_POWER && isFreezePowerKey_) {
1457         MMI_HILOGI("Freeze power key");
1458         return true;
1459     }
1460     bool sequencesHandleRet = HandleSequences(key);
1461     if (shortKeysHandleRet) {
1462         launchAbilityCount_ = 0;
1463         isHandleSequence_ = false;
1464         return true;
1465     }
1466     if (sequencesHandleRet) {
1467         isHandleSequence_ = true;
1468         return true;
1469     }
1470     if (key->GetKeyCode() == KeyEvent::KEYCODE_POWER) {
1471         MMI_HILOGI("Handle power key DownStart:%{public}d", isDownStart_);
1472     }
1473     if (key->GetKeyCode() != repeatKey_.keyCode && key->GetKeyAction() == KeyEvent::KEY_ACTION_DOWN) {
1474         MMI_HILOGI("Combination key currentKey:%{public}d, repeatKey:%{public}d",
1475             key->GetKeyCode(), repeatKey_.keyCode);
1476         isDownStart_ = false;
1477     }
1478     if (!isDownStart_) {
1479         HandleRepeatKeys(key);
1480         return false;
1481     } else {
1482         if (HandleRepeatKeys(key)) {
1483             MMI_HILOGI("Handle power key lifting event");
1484             return true;
1485         }
1486     }
1487     count_ = 0;
1488     repeatKeyCountMap_.clear();
1489     isDownStart_ = false;
1490     return false;
1491 }
1492 
InitKeyObserver()1493 void KeyCommandHandler::InitKeyObserver()
1494 {
1495     if (!isParseStatusConfig_) {
1496         ParseStatusConfigObserver();
1497         isParseStatusConfig_ = true;
1498     }
1499     if (!isKnuckleSwitchConfig_) {
1500         CreateStatusConfigObserver(knuckleSwitch_);
1501         CreateKnuckleConfigObserver(screenshotSwitch_);
1502         CreateKnuckleConfigObserver(recordSwitch_);
1503         isKnuckleSwitchConfig_ = true;
1504     }
1505 }
1506 
1507 #ifdef OHOS_BUILD_ENABLE_KEYBOARD
OnHandleEvent(const std::shared_ptr<KeyEvent> key)1508 bool KeyCommandHandler::OnHandleEvent(const std::shared_ptr<KeyEvent> key)
1509 {
1510     CALL_DEBUG_ENTER;
1511     CHKPF(key);
1512     HandlePointerVisibleKeys(key);
1513     if (HandleEvent(key)) {
1514         return true;
1515     }
1516 
1517     if (specialKeys_.find(key->GetKeyCode()) != specialKeys_.end()) {
1518         HandleSpecialKeys(key->GetKeyCode(), key->GetAction());
1519         return true;
1520     }
1521 
1522     if (IsSpecialType(key->GetKeyCode(), SpecialType::SUBSCRIBER_BEFORE_DELAY)) {
1523         auto tmpKey = KeyEvent::Clone(key);
1524         int32_t timerId = TimerMgr->AddTimer(SPECIAL_KEY_DOWN_DELAY, 1, [this, tmpKey] () {
1525             MMI_HILOGD("Timer callback");
1526             auto it = specialTimers_.find(tmpKey->GetKeyCode());
1527             if (it != specialTimers_.end() && !it->second.empty()) {
1528                 it->second.pop_front();
1529             }
1530             auto handler = InputHandler->GetSubscriberHandler();
1531             CHKPV(handler);
1532             handler->HandleKeyEvent(tmpKey);
1533         });
1534         if (timerId < 0) {
1535             DfxHisysevent::ReportFailHandleKey("OnHandleEvent", key->GetKeyCode(),
1536                 DfxHisysevent::KEY_ERROR_CODE::FAILED_TIMER);
1537             MMI_HILOGE("Add timer failed");
1538             return false;
1539         }
1540 
1541         auto it = specialTimers_.find(key->GetKeyCode());
1542         if (it == specialTimers_.end()) {
1543             std::list<int32_t> timerIds;
1544             timerIds.push_back(timerId);
1545             auto it = specialTimers_.emplace(key->GetKeyCode(), timerIds);
1546             if (!it.second) {
1547                 MMI_HILOGE("Keycode duplicated");
1548                 return false;
1549             }
1550         } else {
1551             it->second.push_back(timerId);
1552         }
1553         MMI_HILOGD("Add timer success");
1554         return true;
1555     }
1556     return false;
1557 }
1558 #endif // OHOS_BUILD_ENABLE_KEYBOARD
1559 
1560 #if defined(OHOS_BUILD_ENABLE_POINTER) || defined(OHOS_BUILD_ENABLE_TOUCH)
OnHandleEvent(const std::shared_ptr<PointerEvent> pointer)1561 bool KeyCommandHandler::OnHandleEvent(const std::shared_ptr<PointerEvent> pointer)
1562 {
1563     CALL_DEBUG_ENTER;
1564     CHKPF(pointer);
1565     STYLUS_HANDLER->SetLastEventState(false);
1566     if (!isParseConfig_) {
1567         if (!ParseConfig()) {
1568             MMI_HILOGE("Parse configFile failed");
1569             return false;
1570         }
1571         isParseConfig_ = true;
1572     }
1573     if (!isParseLongPressConfig_) {
1574         if (!ParseLongPressConfig()) {
1575             MMI_HILOGE("Parse long press configFile failed");
1576         }
1577         isParseLongPressConfig_ = true;
1578     }
1579     return HandleMulFingersTap(pointer);
1580 }
1581 #endif // OHOS_BUILD_ENABLE_POINTER || OHOS_BUILD_ENABLE_TOUCH
1582 
HandleRepeatKeys(const std::shared_ptr<KeyEvent> keyEvent)1583 bool KeyCommandHandler::HandleRepeatKeys(const std::shared_ptr<KeyEvent> keyEvent)
1584 {
1585     CALL_DEBUG_ENTER;
1586     CHKPF(keyEvent);
1587     if (repeatKeys_.empty()) {
1588         MMI_HILOGD("No sequences configuration data");
1589         return false;
1590     }
1591 
1592     bool isLaunched = false;
1593     bool waitRepeatKey = false;
1594 
1595     for (RepeatKey& item : repeatKeys_) {
1596         if (CheckSpecialRepeatKey(item, keyEvent)) {
1597             launchAbilityCount_ = 0;
1598             MMI_HILOGI("Skip repeatKey");
1599             return false;
1600         }
1601         if (HandleKeyUpCancel(item, keyEvent)) {
1602             MMI_HILOGI("Cancel repeatKey");
1603             DfxHisysevent::ReportKeyEvent("cancel");
1604             return false;
1605         }
1606         if (HandleRepeatKeyCount(item, keyEvent)) {
1607             break;
1608         }
1609     }
1610 
1611     for (RepeatKey& item : repeatKeys_) {
1612         bool isRepeatKey = HandleRepeatKey(item, isLaunched, keyEvent);
1613         if (isRepeatKey) {
1614             waitRepeatKey = true;
1615         }
1616     }
1617     MMI_HILOGI("Handle repeat key, isLaunched:%{public}d, waitRepeatKey:%{public}d",
1618         isLaunched, waitRepeatKey);
1619     return isLaunched || waitRepeatKey;
1620 }
1621 
IsMusicActivate()1622 bool KeyCommandHandler::IsMusicActivate()
1623 {
1624     return InputScreenCaptureAgent::GetInstance().IsMusicActivate();
1625 }
1626 
HandleRepeatKeyOwnCount(const RepeatKey & item)1627 void KeyCommandHandler::HandleRepeatKeyOwnCount(const RepeatKey &item)
1628 {
1629     if (item.ability.bundleName == SOS_BUNDLE_NAME) {
1630         if (downActionTime_ - lastDownActionTime_ < item.delay) {
1631             repeatKeyCountMap_[item.ability.bundleName]++;
1632         }
1633     } else if (downActionTime_ - upActionTime_ < item.delay) {
1634         repeatKeyCountMap_[item.ability.bundleName]++;
1635     }
1636 }
1637 
HandleRepeatKey(const RepeatKey & item,bool & isLaunched,const std::shared_ptr<KeyEvent> keyEvent)1638 bool KeyCommandHandler::HandleRepeatKey(const RepeatKey &item, bool &isLaunched,
1639     const std::shared_ptr<KeyEvent> keyEvent)
1640 {
1641     CALL_DEBUG_ENTER;
1642     CHKPF(keyEvent);
1643     if (keyEvent->GetKeyCode() != item.keyCode) {
1644         return false;
1645     }
1646     if (!isDownStart_) {
1647         return false;
1648     }
1649     if (keyEvent->GetKeyAction() != KeyEvent::KEY_ACTION_DOWN ||
1650         (count_ > maxCount_ && keyEvent->GetKeyCode() == KeyEvent::KEYCODE_POWER)) {
1651         MMI_HILOGI("The isDownStart:%{public}d", isDownStart_);
1652         if (isDownStart_) {
1653             HandleSpecialKeys(keyEvent->GetKeyCode(), keyEvent->GetKeyAction());
1654         }
1655         return true;
1656     }
1657     auto it = repeatKeyCountMap_.find(item.ability.bundleName);
1658     if (it == repeatKeyCountMap_.end()) {
1659         lastDownActionTime_ = downActionTime_;
1660         if (item.ability.bundleName != SOS_BUNDLE_NAME ||
1661             downActionTime_ - lastVolumeDownActionTime_ > SOS_INTERVAL_TIMES) {
1662             repeatKeyCountMap_.emplace(item.ability.bundleName, 1);
1663             return true;
1664         }
1665         return false;
1666     }
1667     HandleRepeatKeyOwnCount(item);
1668     lastDownActionTime_ = downActionTime_;
1669     if (repeatKeyCountMap_[item.ability.bundleName] == item.times) {
1670         if (!item.statusConfig.empty()) {
1671             bool statusValue = true;
1672             auto ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID)
1673                 .GetBoolValue(item.statusConfig, statusValue);
1674             if (ret != RET_OK) {
1675                 MMI_HILOGE("Get value from setting data fail");
1676                 DfxHisysevent::ReportFailHandleKey("HandleRepeatKey", keyEvent->GetKeyCode(),
1677                     DfxHisysevent::KEY_ERROR_CODE::ERROR_RETURN_VALUE);
1678                 return false;
1679             }
1680             if (!statusValue) {
1681                 MMI_HILOGE("Get value from setting data, result is false");
1682                 return false;
1683             }
1684         }
1685         if (repeatKeyMaxTimes_.find(item.keyCode) != repeatKeyMaxTimes_.end()) {
1686             launchAbilityCount_ = count_;
1687             if (item.times < repeatKeyMaxTimes_[item.keyCode]) {
1688                 return HandleRepeatKeyAbility(item, isLaunched, keyEvent, false);
1689             }
1690             return HandleRepeatKeyAbility(item, isLaunched, keyEvent, true);
1691         }
1692     }
1693     if (count_ > item.times && repeatKeyMaxTimes_.find(item.keyCode) != repeatKeyMaxTimes_.end() &&
1694         repeatKeyTimerIds_.find(item.ability.bundleName) != repeatKeyTimerIds_.end()) {
1695         if (count_ < repeatKeyMaxTimes_[item.keyCode] && repeatKeyTimerIds_[item.ability.bundleName] >= 0) {
1696             TimerMgr->RemoveTimer(repeatKeyTimerIds_[item.ability.bundleName]);
1697             repeatKeyTimerIds_.erase(item.ability.bundleName);
1698             return true;
1699         }
1700     }
1701     return true;
1702 }
1703 
HandleRepeatKeyAbility(const RepeatKey & item,bool & isLaunched,const std::shared_ptr<KeyEvent> keyEvent,bool isMaxTimes)1704 bool KeyCommandHandler::HandleRepeatKeyAbility(const RepeatKey &item, bool &isLaunched,
1705     const std::shared_ptr<KeyEvent> keyEvent, bool isMaxTimes)
1706 {
1707     if (!isMaxTimes) {
1708         int64_t delaytime = intervalTime_ - (downActionTime_ - upActionTime_);
1709         int32_t timerId = TimerMgr->AddTimer(
1710             delaytime / SECONDS_SYSTEM, 1, [this, item, &isLaunched, keyEvent] () {
1711             LaunchRepeatKeyAbility(item, isLaunched, keyEvent);
1712             auto it = repeatKeyTimerIds_.find(item.ability.bundleName);
1713             if (it != repeatKeyTimerIds_.end()) {
1714                 repeatKeyTimerIds_.erase(it);
1715             }
1716         });
1717         if (timerId < 0) {
1718             DfxHisysevent::ReportFailHandleKey("HandleRepeatKeyAbility", keyEvent->GetKeyCode(),
1719                 DfxHisysevent::KEY_ERROR_CODE::FAILED_TIMER);
1720             return false;
1721         }
1722         if (repeatTimerId_ >= 0) {
1723             TimerMgr->RemoveTimer(repeatTimerId_);
1724             repeatTimerId_ = DEFAULT_VALUE;
1725             isHandleSequence_ = false;
1726         }
1727         if (repeatKeyTimerIds_.find(item.ability.bundleName) == repeatKeyTimerIds_.end()) {
1728             repeatKeyTimerIds_.emplace(item.ability.bundleName, timerId);
1729             return true;
1730         }
1731         repeatKeyTimerIds_[item.ability.bundleName] = timerId;
1732         return true;
1733     }
1734     LaunchRepeatKeyAbility(item, isLaunched, keyEvent);
1735     return true;
1736 }
1737 
LaunchRepeatKeyAbility(const RepeatKey & item,bool & isLaunched,const std::shared_ptr<KeyEvent> keyEvent)1738 void KeyCommandHandler::LaunchRepeatKeyAbility(const RepeatKey &item, bool &isLaunched,
1739     const std::shared_ptr<KeyEvent> keyEvent)
1740 {
1741     BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_REPEAT_KEY, item.ability.bundleName);
1742     DfxHisysevent::ReportKeyEvent(item.ability.bundleName);
1743     LaunchAbility(item.ability);
1744     BytraceAdapter::StopLaunchAbility();
1745     repeatKeyCountMap_.clear();
1746     isLaunched = true;
1747     auto subscriberHandler = InputHandler->GetSubscriberHandler();
1748     CHKPV(subscriberHandler);
1749     auto keyEventCancel = std::make_shared<KeyEvent>(*keyEvent);
1750     keyEventCancel->SetKeyAction(KeyEvent::KEY_ACTION_CANCEL);
1751     subscriberHandler->HandleKeyEvent(keyEventCancel);
1752 }
1753 
SetIsFreezePowerKey(const std::string pageName)1754 int32_t KeyCommandHandler::SetIsFreezePowerKey(const std::string pageName)
1755 {
1756     CALL_INFO_TRACE;
1757     std::lock_guard<std::mutex> lock(mutex_);
1758     if (pageName != "SosCountdown") {
1759         isFreezePowerKey_ = false;
1760         return RET_OK;
1761     }
1762     isFreezePowerKey_ = true;
1763     sosLaunchTime_ = OHOS::MMI::GetSysClockTime();
1764     count_ = 0;
1765     launchAbilityCount_ = 0;
1766     repeatKeyCountMap_.clear();
1767     if (sosDelayTimerId_ >= 0) {
1768         TimerMgr->RemoveTimer(sosDelayTimerId_);
1769         sosDelayTimerId_ = DEFAULT_VALUE;
1770     }
1771     int32_t timerId = TimerMgr->AddTimer(
1772         SOS_COUNT_DOWN_TIMES / SECONDS_SYSTEM, 1, [this] () {
1773         MMI_HILOGW("Timeout, restore the power button");
1774         isFreezePowerKey_ = false;
1775     });
1776     if (timerId < 0) {
1777         MMI_HILOGE("Add timer failed");
1778         isFreezePowerKey_ = false;
1779         return RET_ERR;
1780     }
1781     return RET_OK;
1782 }
1783 
HandleKeyUpCancel(const RepeatKey & item,const std::shared_ptr<KeyEvent> keyEvent)1784 bool KeyCommandHandler::HandleKeyUpCancel(const RepeatKey &item, const std::shared_ptr<KeyEvent> keyEvent)
1785 {
1786     CALL_DEBUG_ENTER;
1787     CHKPF(keyEvent);
1788     if (keyEvent->GetKeyCode() == item.keyCode && keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_CANCEL) {
1789         isKeyCancel_ = true;
1790         isDownStart_ = false;
1791         count_ = 0;
1792         repeatKeyCountMap_.clear();
1793         DfxHisysevent::ReportKeyEvent("cancel");
1794         return true;
1795     }
1796     return false;
1797 }
1798 
HandleRepeatKeyCount(const RepeatKey & item,const std::shared_ptr<KeyEvent> keyEvent)1799 bool KeyCommandHandler::HandleRepeatKeyCount(const RepeatKey &item, const std::shared_ptr<KeyEvent> keyEvent)
1800 {
1801     CALL_DEBUG_ENTER;
1802     CHKPF(keyEvent);
1803 
1804     if (keyEvent->GetKeyCode() == item.keyCode && keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_UP) {
1805         upActionTime_ = keyEvent->GetActionTime();
1806         repeatKey_.keyCode = item.keyCode;
1807         repeatKey_.keyAction = keyEvent->GetKeyAction();
1808         int64_t intervalTime = intervalTime_;
1809         if (item.keyCode == KeyEvent::KEYCODE_POWER) {
1810             intervalTime = intervalTime_ - (upActionTime_ - downActionTime_);
1811             if (walletLaunchDelayTimes_ != 0) {
1812                 intervalTime = walletLaunchDelayTimes_;
1813             }
1814         }
1815         repeatTimerId_ = TimerMgr->AddTimer(intervalTime / SECONDS_SYSTEM, 1, [this] () {
1816             SendKeyEvent();
1817             repeatTimerId_ = -1;
1818         });
1819         if (repeatTimerId_ < 0) {
1820             return false;
1821         }
1822         return true;
1823     }
1824 
1825     if (keyEvent->GetKeyCode() == item.keyCode && keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_DOWN) {
1826         if (repeatKey_.keyCode != item.keyCode) {
1827             count_ = 1;
1828             repeatKey_.keyCode = item.keyCode;
1829             repeatKey_.keyAction = keyEvent->GetKeyAction();
1830         } else {
1831             if (repeatKey_.keyAction == keyEvent->GetKeyAction()) {
1832                 MMI_HILOGD("Repeat key, reset down status");
1833                 count_ = 0;
1834                 isDownStart_ = false;
1835                 repeatKeyCountMap_.clear();
1836                 return true;
1837             } else {
1838                 repeatKey_.keyAction = keyEvent->GetKeyAction();
1839                 count_++;
1840                 MMI_HILOGD("Repeat count:%{public}d", count_);
1841             }
1842         }
1843         isDownStart_ = true;
1844         downActionTime_ = keyEvent->GetActionTime();
1845         if ((downActionTime_ - upActionTime_) < intervalTime_) {
1846             if (repeatTimerId_ >= 0) {
1847                 TimerMgr->RemoveTimer(repeatTimerId_);
1848                 repeatTimerId_ = -1;
1849                 isHandleSequence_ = false;
1850             }
1851         }
1852         return true;
1853     }
1854     return false;
1855 }
1856 
SendKeyEvent()1857 void KeyCommandHandler::SendKeyEvent()
1858 {
1859     CALL_DEBUG_ENTER;
1860     if (!isHandleSequence_) {
1861         MMI_HILOGD("Launch ability count:%{public}d count:%{public}d", launchAbilityCount_, count_);
1862         for (int32_t i = launchAbilityCount_; i < count_; i++) {
1863             int32_t keycode = repeatKey_.keyCode;
1864             if (IsSpecialType(keycode, SpecialType::KEY_DOWN_ACTION)) {
1865                 HandleSpecialKeys(keycode, KeyEvent::KEY_ACTION_UP);
1866             }
1867             if (count_ == repeatKeyMaxTimes_[keycode] - 1 && keycode == KeyEvent::KEYCODE_POWER) {
1868                 auto keyEventCancel = CreateKeyEvent(keycode, KeyEvent::KEY_ACTION_CANCEL, false);
1869                 CHKPV(keyEventCancel);
1870                 auto handler = InputHandler->GetSubscriberHandler();
1871                 CHKPV(handler);
1872                 handler->HandleKeyEvent(keyEventCancel);
1873                 continue;
1874             }
1875             if (i != 0) {
1876                 auto keyEventDown = CreateKeyEvent(keycode, KeyEvent::KEY_ACTION_DOWN, true);
1877                 CHKPV(keyEventDown);
1878                 auto handler = InputHandler->GetSubscriberHandler();
1879                 CHKPV(handler);
1880                 handler->HandleKeyEvent(keyEventDown);
1881             }
1882 
1883             auto keyEventUp = CreateKeyEvent(keycode, KeyEvent::KEY_ACTION_UP, false);
1884             CHKPV(keyEventUp);
1885             auto handler = InputHandler->GetSubscriberHandler();
1886             CHKPV(handler);
1887             handler->HandleKeyEvent(keyEventUp);
1888         }
1889     }
1890     count_ = 0;
1891     repeatKeyCountMap_.clear();
1892     isDownStart_ = false;
1893     isHandleSequence_ = false;
1894     launchAbilityCount_ = 0;
1895 }
1896 
HandleShortKeys(const std::shared_ptr<KeyEvent> keyEvent)1897 bool KeyCommandHandler::HandleShortKeys(const std::shared_ptr<KeyEvent> keyEvent)
1898 {
1899     CALL_DEBUG_ENTER;
1900     CHKPF(keyEvent);
1901     if (shortcutKeys_.empty()) {
1902         MMI_HILOGD("No shortkeys configuration data");
1903         return false;
1904     }
1905     if (IsKeyMatch(lastMatchedKey_, keyEvent)) {
1906         MMI_HILOGD("The same key is waiting timeout, skip");
1907         return true;
1908     }
1909     if (currentLaunchAbilityKey_.timerId >= 0 && IsKeyMatch(currentLaunchAbilityKey_, keyEvent)) {
1910         if (EventLogHelper::IsBetaVersion() && !keyEvent->HasFlag(InputEvent::EVENT_FLAG_PRIVACY_MODE)) {
1911             MMI_HILOGD("Repeat, current key %{public}d has launched ability", currentLaunchAbilityKey_.finalKey);
1912         } else {
1913             MMI_HILOGD("Repeat, current key %d has launched ability", currentLaunchAbilityKey_.finalKey);
1914         }
1915         return true;
1916     }
1917     DfxHisysevent::GetComboStartTime();
1918     if (lastMatchedKey_.timerId >= 0) {
1919         MMI_HILOGD("Remove timer:%{public}d", lastMatchedKey_.timerId);
1920         TimerMgr->RemoveTimer(lastMatchedKey_.timerId);
1921         lastMatchedKey_.timerId = -1;
1922     }
1923     ResetLastMatchedKey();
1924     if (MatchShortcutKeys(keyEvent)) {
1925         return true;
1926     }
1927     return HandleConsumedKeyEvent(keyEvent);
1928 }
1929 
MatchShortcutKeys(const std::shared_ptr<KeyEvent> keyEvent)1930 bool KeyCommandHandler::MatchShortcutKeys(const std::shared_ptr<KeyEvent> keyEvent)
1931 {
1932 #ifdef SHORTCUT_KEY_RULES_ENABLED
1933     if ((keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_UP) &&
1934         KEY_SHORTCUT_MGR->HaveShortcutConsumed(keyEvent)) {
1935         return false;
1936     }
1937 #endif // SHORTCUT_KEY_RULES_ENABLED
1938     bool result = false;
1939     std::vector<ShortcutKey> upAbilities;
1940 
1941     for (auto &item : shortcutKeys_) {
1942         result = MatchShortcutKey(keyEvent, item.second, upAbilities) || result;
1943     }
1944     if (!upAbilities.empty()) {
1945         std::sort(upAbilities.begin(), upAbilities.end(),
1946             [](const ShortcutKey &lShortcutKey, const ShortcutKey &rShortcutKey) -> bool {
1947             return lShortcutKey.keyDownDuration > rShortcutKey.keyDownDuration;
1948         });
1949         ShortcutKey tmpShorteKey = upAbilities.front();
1950         MMI_HILOGI("Start launch ability immediately");
1951 #ifdef SHORTCUT_KEY_RULES_ENABLED
1952         KEY_SHORTCUT_MGR->MarkShortcutConsumed(tmpShorteKey);
1953 #endif // SHORTCUT_KEY_RULES_ENABLED
1954         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_SHORTKEY, tmpShorteKey.ability.bundleName);
1955         LaunchAbility(tmpShorteKey);
1956         DfxHisysevent::ReportKeyEvent(tmpShorteKey.ability.bundleName);
1957         BytraceAdapter::StopLaunchAbility();
1958     }
1959     if (result) {
1960         if (currentLaunchAbilityKey_.finalKey == keyEvent->GetKeyCode()
1961             && keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_UP) {
1962             ResetCurrentLaunchAbilityKey();
1963         }
1964     }
1965     return result;
1966 }
1967 
MatchShortcutKey(std::shared_ptr<KeyEvent> keyEvent,ShortcutKey & shortcutKey,std::vector<ShortcutKey> & upAbilities)1968 bool KeyCommandHandler::MatchShortcutKey(std::shared_ptr<KeyEvent> keyEvent,
1969     ShortcutKey &shortcutKey, std::vector<ShortcutKey> &upAbilities)
1970 {
1971     if (!shortcutKey.statusConfigValue) {
1972         return false;
1973     }
1974     if (!IsKeyMatch(shortcutKey, keyEvent)) {
1975         MMI_HILOGD("Not key matched, next");
1976         return false;
1977     }
1978     int32_t delay = GetKeyDownDurationFromXml(shortcutKey.businessId);
1979     if (delay >= MIN_SHORT_KEY_DOWN_DURATION && delay <= MAX_SHORT_KEY_DOWN_DURATION) {
1980         MMI_HILOGD("User defined new short key down duration:%{public}d", delay);
1981         shortcutKey.keyDownDuration = delay;
1982     }
1983     shortcutKey.Print();
1984 
1985     if (shortcutKey.triggerType == KeyEvent::KEY_ACTION_DOWN) {
1986         return HandleKeyDown(shortcutKey);
1987     } else if (shortcutKey.triggerType == KeyEvent::KEY_ACTION_UP) {
1988         bool handleResult = HandleKeyUp(keyEvent, shortcutKey);
1989         if (handleResult && shortcutKey.keyDownDuration > 0) {
1990             upAbilities.push_back(shortcutKey);
1991         }
1992         return handleResult;
1993     } else {
1994         return HandleKeyCancel(shortcutKey);
1995     }
1996 }
1997 
HandleConsumedKeyEvent(const std::shared_ptr<KeyEvent> keyEvent)1998 bool KeyCommandHandler::HandleConsumedKeyEvent(const std::shared_ptr<KeyEvent> keyEvent)
1999 {
2000     CALL_DEBUG_ENTER;
2001     CHKPF(keyEvent);
2002     if (currentLaunchAbilityKey_.finalKey == keyEvent->GetKeyCode()
2003         && keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_UP) {
2004         MMI_HILOGI("Handle consumed key event, cancel opration");
2005         ResetCurrentLaunchAbilityKey();
2006         repeatKey_.keyCode = -1;
2007         repeatKey_.keyAction = -1;
2008         auto keyEventCancel = std::make_shared<KeyEvent>(*keyEvent);
2009         keyEventCancel->SetKeyAction(KeyEvent::KEY_ACTION_CANCEL);
2010         auto inputEventNormalizeHandler = InputHandler->GetEventNormalizeHandler();
2011         CHKPF(inputEventNormalizeHandler);
2012         inputEventNormalizeHandler->HandleKeyEvent(keyEventCancel);
2013         return true;
2014     }
2015     return false;
2016 }
2017 
IsRepeatKeyEvent(const SequenceKey & sequenceKey)2018 bool KeyCommandHandler::IsRepeatKeyEvent(const SequenceKey &sequenceKey)
2019 {
2020     for (size_t i = keys_.size(); i > 0; --i) {
2021         if (keys_[i-1].keyCode == sequenceKey.keyCode) {
2022             if (keys_[i-1].keyAction == sequenceKey.keyAction) {
2023                 MMI_HILOGI("Is repeat key, keyCode:%d", sequenceKey.keyCode);
2024                 return true;
2025             }
2026             MMI_HILOGI("Is not repeat key");
2027             return false;
2028         }
2029     }
2030     return false;
2031 }
2032 
IsActiveSequenceRepeating(std::shared_ptr<KeyEvent> keyEvent) const2033 bool KeyCommandHandler::IsActiveSequenceRepeating(std::shared_ptr<KeyEvent> keyEvent) const
2034 {
2035     return (sequenceOccurred_ && !keys_.empty() &&
2036             (keys_.back().keyCode == keyEvent->GetKeyCode()) &&
2037             (keys_.back().keyAction == KeyEvent::KEY_ACTION_DOWN) &&
2038             (keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_DOWN));
2039 }
2040 
MarkActiveSequence(bool active)2041 void KeyCommandHandler::MarkActiveSequence(bool active)
2042 {
2043     sequenceOccurred_ = active;
2044 }
2045 
HandleSequences(const std::shared_ptr<KeyEvent> keyEvent)2046 bool KeyCommandHandler::HandleSequences(const std::shared_ptr<KeyEvent> keyEvent)
2047 {
2048     CALL_DEBUG_ENTER;
2049     CHKPF(keyEvent);
2050     std::string screenStatus = DISPLAY_MONITOR->GetScreenStatus();
2051     if (screenStatus == EventFwk::CommonEventSupport::COMMON_EVENT_SCREEN_OFF) {
2052         if (keyEvent->GetKeyCode() == KeyEvent::KEYCODE_POWER) {
2053             MMI_HILOGI("The screen is currently off and the power button needs to respond");
2054             return false;
2055         }
2056     }
2057     if (IsActiveSequenceRepeating(keyEvent)) {
2058         MMI_HILOGD("Skip repeating key(%{private}d) in active sequence", keyEvent->GetKeyCode());
2059         return true;
2060     }
2061     MarkActiveSequence(false);
2062     if (matchedSequence_.timerId >= 0 && keyEvent->GetKeyAction() == KeyEvent::KEY_ACTION_UP) {
2063         MMI_HILOGI("Screen locked, remove matchedSequence timer:%{public}d", matchedSequence_.timerId);
2064         TimerMgr->RemoveTimer(matchedSequence_.timerId);
2065         matchedSequence_.timerId = -1;
2066     }
2067     if (sequences_.empty()) {
2068         MMI_HILOGD("No sequences configuration data");
2069         return false;
2070     }
2071 
2072     if (!AddSequenceKey(keyEvent)) {
2073         MMI_HILOGD("Add new sequence key failed");
2074         return false;
2075     }
2076 
2077     if (filterSequences_.empty()) {
2078         filterSequences_ = sequences_;
2079     }
2080 
2081     bool isLaunchAbility = false;
2082     for (auto iter = filterSequences_.begin(); iter != filterSequences_.end();) {
2083         if (!HandleSequence((*iter), isLaunchAbility)) {
2084             filterSequences_.erase(iter);
2085             continue;
2086         }
2087         ++iter;
2088     }
2089 
2090     if (filterSequences_.empty()) {
2091         MMI_HILOGD("No sequences matched");
2092         keys_.clear();
2093         return false;
2094     }
2095 
2096     if (isLaunchAbility) {
2097         MarkActiveSequence(true);
2098         for (const auto& item : keys_) {
2099             if (IsSpecialType(item.keyCode, SpecialType::KEY_DOWN_ACTION)) {
2100                 HandleSpecialKeys(item.keyCode, item.keyAction);
2101             }
2102             auto handler = InputHandler->GetSubscriberHandler();
2103             CHKPF(handler);
2104             handler->RemoveSubscriberKeyUpTimer(item.keyCode);
2105             RemoveSubscribedTimer(item.keyCode);
2106         }
2107     }
2108     return isLaunchAbility;
2109 }
2110 
AddSequenceKey(const std::shared_ptr<KeyEvent> keyEvent)2111 bool KeyCommandHandler::AddSequenceKey(const std::shared_ptr<KeyEvent> keyEvent)
2112 {
2113     CALL_DEBUG_ENTER;
2114     CHKPF(keyEvent);
2115     SequenceKey sequenceKey;
2116     sequenceKey.keyCode = keyEvent->GetKeyCode();
2117     sequenceKey.keyAction = keyEvent->GetKeyAction();
2118     sequenceKey.actionTime = keyEvent->GetActionTime();
2119     size_t size = keys_.size();
2120     if (size > 0) {
2121         if (keys_[size - 1].actionTime > sequenceKey.actionTime) {
2122             MMI_HILOGE("The current event time is greater than the last event time");
2123             ResetSequenceKeys();
2124             return false;
2125         }
2126         if ((sequenceKey.actionTime - keys_[size - 1].actionTime) > MAX_DELAY_TIME) {
2127             MMI_HILOGD("The delay time is greater than the maximum delay time");
2128             ResetSequenceKeys();
2129         } else {
2130             if (IsRepeatKeyEvent(sequenceKey)) {
2131                 MMI_HILOGD("This is a repeat key event, don't add");
2132                 return false;
2133             }
2134             keys_[size - 1].delay = sequenceKey.actionTime - keys_[size - 1].actionTime;
2135             InterruptTimers();
2136         }
2137     }
2138     if (size > MAX_SEQUENCEKEYS_NUM) {
2139         DfxHisysevent::ReportFailHandleKey("AddSequenceKey", keyEvent->GetKeyCode(),
2140             DfxHisysevent::KEY_ERROR_CODE::INVALID_PARAMETER);
2141         MMI_HILOGD("The save key size more than the max size");
2142         return false;
2143     }
2144     keys_.push_back(sequenceKey);
2145     return true;
2146 }
2147 
HandleScreenLocked(Sequence & sequence,bool & isLaunchAbility)2148 bool KeyCommandHandler::HandleScreenLocked(Sequence& sequence, bool &isLaunchAbility)
2149 {
2150     sequence.timerId = TimerMgr->AddTimer(LONG_ABILITY_START_DELAY, 1, [this, &sequence] () {
2151         MMI_HILOGI("Timer callback");
2152         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_SEQUENCE, sequence.ability.bundleName);
2153         DfxHisysevent::ReportKeyEvent(sequence.ability.bundleName);
2154         LaunchAbility(sequence);
2155         sequence.timerId = -1;
2156         BytraceAdapter::StopLaunchAbility();
2157     });
2158     if (sequence.timerId < 0) {
2159         MMI_HILOGE("Add Timer failed");
2160         return false;
2161     }
2162     MMI_HILOGI("Add timer success");
2163     matchedSequence_ = sequence;
2164     isLaunchAbility = true;
2165     return true;
2166 }
2167 
HandleNormalSequence(Sequence & sequence,bool & isLaunchAbility)2168 bool KeyCommandHandler::HandleNormalSequence(Sequence& sequence, bool &isLaunchAbility)
2169 {
2170     if (sequence.abilityStartDelay == 0) {
2171         MMI_HILOGI("Start launch ability immediately");
2172         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_SEQUENCE, sequence.ability.bundleName);
2173         LaunchAbility(sequence);
2174         DfxHisysevent::ReportKeyEvent(sequence.ability.bundleName);
2175         BytraceAdapter::StopLaunchAbility();
2176         isLaunchAbility = true;
2177         return true;
2178     }
2179     sequence.timerId = TimerMgr->AddTimer(sequence.abilityStartDelay, 1, [this, &sequence] () {
2180         MMI_HILOGI("Timer callback");
2181         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_SEQUENCE, sequence.ability.bundleName);
2182         LaunchAbility(sequence);
2183         DfxHisysevent::ReportKeyEvent(sequence.ability.bundleName);
2184         sequence.timerId = -1;
2185         BytraceAdapter::StopLaunchAbility();
2186     });
2187     if (sequence.timerId < 0) {
2188         MMI_HILOGE("Add Timer failed");
2189         DfxHisysevent::ReportFailLaunchAbility(sequence.ability.bundleName,
2190             DfxHisysevent::KEY_ERROR_CODE::FAILED_TIMER);
2191         return false;
2192     }
2193     MMI_HILOGI("Add timer success");
2194     isLaunchAbility = true;
2195     return true;
2196 }
2197 
HandleMatchedSequence(Sequence & sequence,bool & isLaunchAbility)2198 bool KeyCommandHandler::HandleMatchedSequence(Sequence& sequence, bool &isLaunchAbility)
2199 {
2200     std::string screenStatus = DISPLAY_MONITOR->GetScreenStatus();
2201     bool isScreenLocked = DISPLAY_MONITOR->GetScreenLocked();
2202     MMI_HILOGI("The screenStatus:%{public}s, isScreenLocked:%{public}d", screenStatus.c_str(), isScreenLocked);
2203     std::string bundleName = sequence.ability.bundleName;
2204     std::string matchName = ".screenshot";
2205     if (bundleName.find(matchName) != std::string::npos) {
2206         bundleName = bundleName.substr(bundleName.size() - matchName.size());
2207     }
2208     if (screenStatus == EventFwk::CommonEventSupport::COMMON_EVENT_SCREEN_OFF) {
2209         if (bundleName == matchName) {
2210             MMI_HILOGI("Screen off, screenshot invalid");
2211             return false;
2212         }
2213     } else {
2214         if (bundleName == matchName && isScreenLocked) {
2215             MMI_HILOGI("Screen locked, screenshot delay 2000 milisecond");
2216             return HandleScreenLocked(sequence, isLaunchAbility);
2217         }
2218     }
2219     return HandleNormalSequence(sequence, isLaunchAbility);
2220 }
2221 
HandleSequence(Sequence & sequence,bool & isLaunchAbility)2222 bool KeyCommandHandler::HandleSequence(Sequence &sequence, bool &isLaunchAbility)
2223 {
2224     CALL_DEBUG_ENTER;
2225     size_t keysSize = keys_.size();
2226     size_t sequenceKeysSize = sequence.sequenceKeys.size();
2227     if (!sequence.statusConfigValue) {
2228         return false;
2229     }
2230     if (keysSize > sequenceKeysSize) {
2231         MMI_HILOGI("The save sequence not matching ability sequence");
2232         return false;
2233     }
2234     for (size_t i = 0; i < keysSize; ++i) {
2235         if (keys_[i] != sequence.sequenceKeys[i]) {
2236             MMI_HILOGD("The keyCode or keyAction not matching");
2237             return false;
2238         }
2239         int64_t delay = sequence.sequenceKeys[i].delay;
2240         if (((i + 1) != keysSize) && (delay != 0) && (keys_[i].delay >= delay)) {
2241             MMI_HILOGD("Delay is not matching");
2242             return false;
2243         }
2244     }
2245     if (keysSize == sequenceKeysSize) {
2246         std::ostringstream oss;
2247         oss << sequence;
2248         MMI_HILOGI("SequenceKey matched:%{public}s", oss.str().c_str());
2249         return HandleMatchedSequence(sequence, isLaunchAbility);
2250     }
2251     return true;
2252 }
2253 
HandleMulFingersTap(const std::shared_ptr<PointerEvent> pointerEvent)2254 bool KeyCommandHandler::HandleMulFingersTap(const std::shared_ptr<PointerEvent> pointerEvent)
2255 {
2256     CALL_DEBUG_ENTER;
2257     if (pointerEvent->GetPointerAction() == PointerEvent::POINTER_ACTION_TRIPTAP) {
2258         MMI_HILOGI("The touchpad trip tap will launch ability");
2259         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_MULTI_FINGERS, threeFingersTap_.ability.bundleName);
2260         LaunchAbility(threeFingersTap_.ability, NO_DELAY);
2261         BytraceAdapter::StopLaunchAbility();
2262         return true;
2263     }
2264     return false;
2265 }
2266 
IsKeyMatch(const ShortcutKey & shortcutKey,const std::shared_ptr<KeyEvent> & key)2267 bool KeyCommandHandler::IsKeyMatch(const ShortcutKey &shortcutKey, const std::shared_ptr<KeyEvent> &key)
2268 {
2269     CALL_DEBUG_ENTER;
2270     CHKPF(key);
2271     if ((key->GetKeyCode() != shortcutKey.finalKey) || (shortcutKey.triggerType != key->GetKeyAction())) {
2272         DfxHisysevent::ReportFailHandleKey("IsKeyMatch", key->GetKeyCode(),
2273             DfxHisysevent::KEY_ERROR_CODE::INVALID_PARAMETER);
2274         return false;
2275     }
2276     if ((shortcutKey.preKeys.size() + 1) != key->GetKeyItems().size()) {
2277         return false;
2278     }
2279     for (const auto &item : key->GetKeyItems()) {
2280         int32_t keyCode = item.GetKeyCode();
2281         if (SkipFinalKey(keyCode, key)) {
2282             continue;
2283         }
2284         if (shortcutKey.preKeys.find(keyCode) == shortcutKey.preKeys.end()) {
2285             return false;
2286         }
2287     }
2288     MMI_HILOGD("Leave, key matched");
2289     return true;
2290 }
2291 
SkipFinalKey(const int32_t keyCode,const std::shared_ptr<KeyEvent> & key)2292 bool KeyCommandHandler::SkipFinalKey(const int32_t keyCode, const std::shared_ptr<KeyEvent> &key)
2293 {
2294     CHKPF(key);
2295     return keyCode == key->GetKeyCode();
2296 }
2297 
HandleKeyDown(ShortcutKey & shortcutKey)2298 bool KeyCommandHandler::HandleKeyDown(ShortcutKey &shortcutKey)
2299 {
2300     CALL_DEBUG_ENTER;
2301     if (shortcutKey.keyDownDuration == 0) {
2302         MMI_HILOGI("Start launch ability immediately");
2303 #ifdef SHORTCUT_KEY_RULES_ENABLED
2304         KEY_SHORTCUT_MGR->MarkShortcutConsumed(shortcutKey);
2305 #endif // SHORTCUT_KEY_RULES_ENABLED
2306         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_SHORTKEY, shortcutKey.ability.bundleName);
2307         LaunchAbility(shortcutKey);
2308         DfxHisysevent::ReportKeyEvent(shortcutKey.ability.bundleName);
2309         BytraceAdapter::StopLaunchAbility();
2310         return true;
2311     }
2312     shortcutKey.timerId = TimerMgr->AddTimer(shortcutKey.keyDownDuration, 1, [this, &shortcutKey] () {
2313         MMI_HILOGI("Timer callback");
2314 #ifdef SHORTCUT_KEY_RULES_ENABLED
2315         KEY_SHORTCUT_MGR->MarkShortcutConsumed(shortcutKey);
2316 #endif // SHORTCUT_KEY_RULES_ENABLED
2317         currentLaunchAbilityKey_ = shortcutKey;
2318         shortcutKey.timerId = -1;
2319         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_SHORTKEY, shortcutKey.ability.bundleName);
2320         LaunchAbility(shortcutKey);
2321         DfxHisysevent::ReportKeyEvent(shortcutKey.ability.bundleName);
2322         BytraceAdapter::StopLaunchAbility();
2323     });
2324     if (shortcutKey.timerId < 0) {
2325         MMI_HILOGE("Add Timer failed");
2326         DfxHisysevent::ReportFailLaunchAbility(shortcutKey.ability.bundleName,
2327             DfxHisysevent::KEY_ERROR_CODE::FAILED_TIMER);
2328         return false;
2329     }
2330     MMI_HILOGI("Add timer success");
2331     lastMatchedKey_ = shortcutKey;
2332     auto handler = InputHandler->GetSubscriberHandler();
2333     CHKPF(handler);
2334     if (handler->IsKeyEventSubscribed(shortcutKey.finalKey, shortcutKey.triggerType)) {
2335         MMI_HILOGI("Current shortcutKey %d is subSubcribed", shortcutKey.finalKey);
2336         return false;
2337     }
2338     return true;
2339 }
2340 
GetKeyDownDurationFromXml(const std::string & businessId)2341 int32_t KeyCommandHandler::GetKeyDownDurationFromXml(const std::string &businessId)
2342 {
2343     CALL_DEBUG_ENTER;
2344     return PREFERENCES_MGR->GetShortKeyDuration(businessId);
2345 }
2346 
HandleKeyUp(const std::shared_ptr<KeyEvent> & keyEvent,const ShortcutKey & shortcutKey)2347 bool KeyCommandHandler::HandleKeyUp(const std::shared_ptr<KeyEvent> &keyEvent, const ShortcutKey &shortcutKey)
2348 {
2349     CALL_DEBUG_ENTER;
2350     CHKPF(keyEvent);
2351     if (shortcutKey.keyDownDuration == 0) {
2352         MMI_HILOGI("Start launch ability immediately");
2353         BytraceAdapter::StartLaunchAbility(KeyCommandType::TYPE_SHORTKEY, shortcutKey.ability.bundleName);
2354         LaunchAbility(shortcutKey);
2355         DfxHisysevent::ReportKeyEvent(shortcutKey.ability.bundleName);
2356         BytraceAdapter::StopLaunchAbility();
2357         return true;
2358     }
2359     std::optional<KeyEvent::KeyItem> keyItem = keyEvent->GetKeyItem();
2360     if (!keyItem) {
2361         MMI_HILOGE("The keyItem is nullopt");
2362         return false;
2363     }
2364     auto upTime = keyEvent->GetActionTime();
2365     auto downTime = keyItem->GetDownTime();
2366     MMI_HILOGI("The upTime:%{public}" PRId64 ",downTime:%{public}" PRId64 ",keyDownDuration:%{public}d",
2367         upTime, downTime, shortcutKey.keyDownDuration);
2368 
2369     if (upTime - downTime <= static_cast<int64_t>(shortcutKey.keyDownDuration) * FREQUENCY) {
2370         MMI_HILOGI("Skip, upTime - downTime <= duration");
2371         return false;
2372     }
2373     return true;
2374 }
2375 
HandleKeyCancel(ShortcutKey & shortcutKey)2376 bool KeyCommandHandler::HandleKeyCancel(ShortcutKey &shortcutKey)
2377 {
2378     CALL_DEBUG_ENTER;
2379     if (shortcutKey.timerId < 0) {
2380         DfxHisysevent::ReportFailHandleKey("HandleKeyCancel", shortcutKey.finalKey,
2381             DfxHisysevent::KEY_ERROR_CODE::INVALID_PARAMETER);
2382         MMI_HILOGE("Skip, timerid less than 0");
2383     }
2384     auto timerId = shortcutKey.timerId;
2385     shortcutKey.timerId = -1;
2386     TimerMgr->RemoveTimer(timerId);
2387     MMI_HILOGI("The timerId:%{public}d", timerId);
2388     return false;
2389 }
2390 
LaunchAbility(const Ability & ability,int64_t delay)2391 void KeyCommandHandler::LaunchAbility(const Ability &ability, int64_t delay)
2392 {
2393     CALL_DEBUG_ENTER;
2394     if (ability.bundleName.empty()) {
2395         MMI_HILOGW("BundleName is empty");
2396         return;
2397     }
2398     AAFwk::Want want;
2399     want.SetElementName(ability.deviceId, ability.bundleName, ability.abilityName);
2400     want.SetAction(ability.action);
2401     want.SetUri(ability.uri);
2402     want.SetType(ability.type);
2403     for (const auto &entity : ability.entities) {
2404         want.AddEntity(entity);
2405     }
2406     for (const auto &item : ability.params) {
2407         want.SetParam(item.first, item.second);
2408     }
2409     DfxHisysevent::CalcComboStartTimes(delay);
2410     DfxHisysevent::ReportComboStartTimes();
2411     MMI_HILOGW("Start launch ability, bundleName:%{public}s", ability.bundleName.c_str());
2412     auto begin = std::chrono::high_resolution_clock::now();
2413     ErrCode err = AAFwk::AbilityManagerClient::GetInstance()->StartAbility(want);
2414     auto durationMS = std::chrono::duration_cast<std::chrono::milliseconds>(
2415         std::chrono::high_resolution_clock::now() - begin).count();
2416 #ifdef OHOS_BUILD_ENABLE_DFX_RADAR
2417     DfxHisysevent::ReportApiCallTimes(ApiDurationStatistics::Api::ABILITY_MGR_CLIENT_START_ABILITY, durationMS);
2418 #endif // OHOS_BUILD_ENABLE_DFX_RADAR
2419     if (err != ERR_OK) {
2420         MMI_HILOGE("LaunchAbility failed, bundleName:%{public}s, err:%{public}d", ability.bundleName.c_str(), err);
2421         return;
2422     }
2423     int32_t state = NapProcess::GetInstance()->GetNapClientPid();
2424     if (state == REMOVE_OBSERVER) {
2425         MMI_HILOGW("nap client status:%{public}d", state);
2426         return;
2427     }
2428     OHOS::MMI::NapProcess::NapStatusData napData;
2429     napData.pid = -1;
2430     napData.uid = -1;
2431     napData.bundleName = ability.bundleName;
2432     int32_t syncState = ACTIVE_EVENT;
2433     NapProcess::GetInstance()->AddMmiSubscribedEventData(napData, syncState);
2434     NapProcess::GetInstance()->NotifyBundleName(napData, syncState);
2435     MMI_HILOGW("End launch ability, bundleName:%{public}s", ability.bundleName.c_str());
2436     return;
2437 }
2438 
LaunchAbility(const Ability & ability)2439 void KeyCommandHandler::LaunchAbility(const Ability &ability)
2440 {
2441     CALL_DEBUG_ENTER;
2442     AAFwk::Want want;
2443     want.SetElementName(ability.deviceId, ability.bundleName, ability.abilityName);
2444     want.SetAction(ability.action);
2445     want.SetUri(ability.uri);
2446     want.SetType(ability.uri);
2447     for (const auto &entity : ability.entities) {
2448         want.AddEntity(entity);
2449     }
2450     for (const auto &item : ability.params) {
2451         want.SetParam(item.first, item.second);
2452     }
2453 
2454     MMI_HILOGW("Start launch ability, bundleName:%{public}s", ability.bundleName.c_str());
2455     if (ability.abilityType == EXTENSION_ABILITY) {
2456         auto begin = std::chrono::high_resolution_clock::now();
2457         ErrCode err = AAFwk::AbilityManagerClient::GetInstance()->StartExtensionAbility(want, nullptr);
2458         auto durationMS = std::chrono::duration_cast<std::chrono::milliseconds>(
2459         std::chrono::high_resolution_clock::now() - begin).count();
2460 #ifdef OHOS_BUILD_ENABLE_DFX_RADAR
2461         DfxHisysevent::ReportApiCallTimes(ApiDurationStatistics::Api::ABILITY_MGR_START_EXT_ABILITY, durationMS);
2462 #endif // OHOS_BUILD_ENABLE_DFX_RADAR
2463         if (err != ERR_OK) {
2464             MMI_HILOGE("LaunchAbility failed, bundleName:%{public}s, err:%{public}d", ability.bundleName.c_str(), err);
2465         }
2466     } else {
2467         auto begin = std::chrono::high_resolution_clock::now();
2468         ErrCode err = AAFwk::AbilityManagerClient::GetInstance()->StartAbility(want);
2469         auto durationMS = std::chrono::duration_cast<std::chrono::milliseconds>(
2470         std::chrono::high_resolution_clock::now() - begin).count();
2471 #ifdef OHOS_BUILD_ENABLE_DFX_RADAR
2472         DfxHisysevent::ReportApiCallTimes(ApiDurationStatistics::Api::ABILITY_MGR_CLIENT_START_ABILITY, durationMS);
2473 #endif // OHOS_BUILD_ENABLE_DFX_RADAR
2474         if (err != ERR_OK) {
2475             MMI_HILOGE("LaunchAbility failed, bundleName:%{public}s, err:%{public}d", ability.bundleName.c_str(), err);
2476         }
2477         if (err == ERR_OK && ability.bundleName == SOS_BUNDLE_NAME) {
2478             if (isDownStart_) {
2479                 isDownStart_ = false;
2480             }
2481             isFreezePowerKey_ = true;
2482             sosLaunchTime_ = OHOS::MMI::GetSysClockTime();
2483             count_ = 0;
2484             launchAbilityCount_ = 0;
2485             repeatKeyCountMap_.clear();
2486             repeatKey_.keyCode = -1;
2487             repeatKey_.keyAction = -1;
2488             sosDelayTimerId_ = TimerMgr->AddTimer(SOS_DELAY_TIMES / SECONDS_SYSTEM, 1, [this] () {
2489                 isFreezePowerKey_ = false;
2490                 sosDelayTimerId_ = -1;
2491                 MMI_HILOGW("Timeout, restore the power button");
2492             });
2493             if (sosDelayTimerId_ < 0) {
2494                 isFreezePowerKey_ = false;
2495                 MMI_HILOGE("Add timer failed");
2496             }
2497         }
2498     }
2499     MMI_HILOGW("End launch ability, bundleName:%{public}s", ability.bundleName.c_str());
2500 }
2501 
LaunchAbility(const ShortcutKey & key)2502 void KeyCommandHandler::LaunchAbility(const ShortcutKey &key)
2503 {
2504     CALL_INFO_TRACE;
2505     LaunchAbility(key.ability, lastMatchedKey_.keyDownDuration);
2506     ResetLastMatchedKey();
2507 }
2508 
LaunchAbility(const Sequence & sequence)2509 void KeyCommandHandler::LaunchAbility(const Sequence &sequence)
2510 {
2511     CALL_INFO_TRACE;
2512     LaunchAbility(sequence.ability, sequence.abilityStartDelay);
2513 }
2514 
Print() const2515 void ShortcutKey::Print() const
2516 {
2517     for (const auto &prekey: preKeys) {
2518         MMI_HILOGI("Eventkey matched, preKey:%d", prekey);
2519     }
2520     MMI_HILOGI("Eventkey matched, finalKey:%d, bundleName:%{public}s",
2521         finalKey, ability.bundleName.c_str());
2522 }
2523 
RemoveSubscribedTimer(int32_t keyCode)2524 void KeyCommandHandler::RemoveSubscribedTimer(int32_t keyCode)
2525 {
2526     CALL_DEBUG_ENTER;
2527     auto iter = specialTimers_.find(keyCode);
2528     if (iter != specialTimers_.end()) {
2529         for (auto& item : iter->second) {
2530             TimerMgr->RemoveTimer(item);
2531         }
2532         specialTimers_.erase(keyCode);
2533         MMI_HILOGI("Remove timer success");
2534     }
2535 }
2536 
HandleSpecialKeys(int32_t keyCode,int32_t keyAction)2537 void KeyCommandHandler::HandleSpecialKeys(int32_t keyCode, int32_t keyAction)
2538 {
2539     CALL_INFO_TRACE;
2540     auto iter = specialKeys_.find(keyCode);
2541     if (keyAction == KeyEvent::KEY_ACTION_UP) {
2542         if (iter != specialKeys_.end()) {
2543             specialKeys_.erase(iter);
2544             return;
2545         }
2546     }
2547 
2548     if (keyAction == KeyEvent::KEY_ACTION_DOWN) {
2549         if (iter == specialKeys_.end()) {
2550             auto it = specialKeys_.emplace(keyCode, keyAction);
2551             if (!it.second) {
2552                 MMI_HILOGD("KeyCode duplicated");
2553                 return;
2554             }
2555         }
2556     }
2557 }
2558 
InterruptTimers()2559 void KeyCommandHandler::InterruptTimers()
2560 {
2561     for (Sequence& item : filterSequences_) {
2562         if (item.timerId >= 0) {
2563             MMI_HILOGD("The key sequence change, close the timer");
2564             TimerMgr->RemoveTimer(item.timerId);
2565             item.timerId = -1;
2566         }
2567     }
2568 }
2569 
HandlePointerVisibleKeys(const std::shared_ptr<KeyEvent> & keyEvent)2570 void KeyCommandHandler::HandlePointerVisibleKeys(const std::shared_ptr<KeyEvent> &keyEvent)
2571 {
2572     CALL_DEBUG_ENTER;
2573     CHKPV(keyEvent);
2574     if (keyEvent->GetKeyCode() == KeyEvent::KEYCODE_F9 && lastKeyEventCode_ == KeyEvent::KEYCODE_CTRL_LEFT) {
2575         MMI_HILOGI("Force make pointer visible");
2576 #if defined(OHOS_BUILD_ENABLE_POINTER) && defined(OHOS_BUILD_ENABLE_POINTER_DRAWING)
2577         IPointerDrawingManager::GetInstance()->ForceClearPointerVisiableStatus();
2578 #endif // OHOS_BUILD_ENABLE_POINTER && OHOS_BUILD_ENABLE_POINTER_DRAWING
2579     }
2580     lastKeyEventCode_ = keyEvent->GetKeyCode();
2581 }
2582 
2583 
UpdateSettingsXml(const std::string & businessId,int32_t delay)2584 int32_t KeyCommandHandler::UpdateSettingsXml(const std::string &businessId, int32_t delay)
2585 {
2586     CALL_DEBUG_ENTER;
2587     if (businessId.empty() || businessIds_.empty()) {
2588         MMI_HILOGE("The business id or business ids is empty");
2589         return PARAMETER_ERROR;
2590     }
2591     if (std::find(businessIds_.begin(), businessIds_.end(), businessId) == businessIds_.end()) {
2592         MMI_HILOGE("%{public}s not in the config file", businessId.c_str());
2593         return PARAMETER_ERROR;
2594     }
2595     if (delay < MIN_SHORT_KEY_DOWN_DURATION || delay > MAX_SHORT_KEY_DOWN_DURATION) {
2596         MMI_HILOGE("Delay is not in valid range");
2597         return PARAMETER_ERROR;
2598     }
2599     return PREFERENCES_MGR->SetShortKeyDuration(businessId, delay);
2600 }
2601 
GetSingleKnuckleGesture() const2602 KnuckleGesture KeyCommandHandler::GetSingleKnuckleGesture() const
2603 {
2604     return singleKnuckleGesture_;
2605 }
2606 
GetDoubleKnuckleGesture() const2607 KnuckleGesture KeyCommandHandler::GetDoubleKnuckleGesture() const
2608 {
2609     return doubleKnuckleGesture_;
2610 }
2611 
SetKnuckleDoubleTapIntervalTime(int64_t interval)2612 void KeyCommandHandler::SetKnuckleDoubleTapIntervalTime(int64_t interval)
2613 {
2614     CALL_DEBUG_ENTER;
2615     if (interval < 0) {
2616         MMI_HILOGE("Invalid interval time:%{public}" PRId64 "", interval);
2617         return;
2618     }
2619     downToPrevUpTimeConfig_ = interval;
2620 }
2621 
SetKnuckleDoubleTapDistance(float distance)2622 void KeyCommandHandler::SetKnuckleDoubleTapDistance(float distance)
2623 {
2624     CALL_DEBUG_ENTER;
2625     if (distance <= std::numeric_limits<float>::epsilon()) {
2626         MMI_HILOGE("Invalid distance:%{public}f", distance);
2627         return;
2628     }
2629     downToPrevDownDistanceConfig_ = distance;
2630 }
2631 
CheckInputMethodArea(const std::shared_ptr<PointerEvent> touchEvent)2632 bool KeyCommandHandler::CheckInputMethodArea(const std::shared_ptr<PointerEvent> touchEvent)
2633 {
2634     CALL_DEBUG_ENTER;
2635     CHKPF(touchEvent);
2636     int32_t id = touchEvent->GetPointerId();
2637     PointerEvent::PointerItem item;
2638     touchEvent->GetPointerItem(id, item);
2639     int32_t targetWindowId = item.GetTargetWindowId();
2640     int32_t targetDisplayId = touchEvent->GetTargetDisplayId();
2641     auto window = WIN_MGR->GetWindowAndDisplayInfo(targetWindowId, targetDisplayId);
2642     if (!window || (window->windowType != WINDOW_INPUT_METHOD_TYPE && window->windowType != WINDOW_SCREENSHOT_TYPE)) {
2643             return false;
2644     }
2645     return true;
2646 }
2647 
Dump(int32_t fd,const std::vector<std::string> & args)2648 void KeyCommandHandler::Dump(int32_t fd, const std::vector<std::string> &args)
2649 {
2650     static const std::unordered_map<int32_t, std::string> actionMap = { {0, "UNKNOWN"},
2651         {1, "CANCEL"}, {2, "DOWN"}, {3, "UP"} };
2652     CALL_DEBUG_ENTER;
2653     mprintf(fd, "----------------------------- ShortcutKey information ----------------------------\t");
2654     mprintf(fd, "ShortcutKey: count = %zu", shortcutKeys_.size());
2655     for (const auto &item : shortcutKeys_) {
2656         auto &shortcutKey = item.second;
2657         for (const auto &prekey : shortcutKey.preKeys) {
2658             mprintf(fd, "PreKey:%d", prekey);
2659         }
2660         mprintf(fd,
2661             "BusinessId: %s | StatusConfig: %s | StatusConfigValue: %s "
2662             "| FinalKey: %d | keyDownDuration: %d | TriggerType: %d | BundleName: %s | AbilityName: %s "
2663             "| Action: %s \t", shortcutKey.businessId.c_str(), shortcutKey.statusConfig.c_str(),
2664             shortcutKey.statusConfigValue ? "true" : "false", shortcutKey.finalKey, shortcutKey.keyDownDuration,
2665             shortcutKey.triggerType, shortcutKey.ability.bundleName.c_str(), shortcutKey.ability.abilityName.c_str(),
2666             shortcutKey.ability.action.c_str());
2667     }
2668     mprintf(fd, "-------------------------- Sequence information ----------------------------------\t");
2669     mprintf(fd, "Sequence: count = %zu", sequences_.size());
2670     for (const auto &item : sequences_) {
2671         for (const auto& sequenceKey : item.sequenceKeys) {
2672             mprintf(fd, "keyCode: %d | keyAction: %s",
2673                 sequenceKey.keyCode, ConvertKeyActionToString(sequenceKey.keyAction).c_str());
2674         }
2675         mprintf(fd, "BundleName: %s | AbilityName: %s | Action: %s ",
2676             item.ability.bundleName.c_str(), item.ability.abilityName.c_str(), item.ability.action.c_str());
2677     }
2678     mprintf(fd, "-------------------------- ExcludeKey information --------------------------------\t");
2679     mprintf(fd, "ExcludeKey: count = %zu", excludeKeys_.size());
2680     for (const auto &item : excludeKeys_) {
2681         mprintf(fd, "keyCode: %d | keyAction: %s", item.keyCode, ConvertKeyActionToString(item.keyAction).c_str());
2682     }
2683     mprintf(fd, "-------------------------- RepeatKey information ---------------------------------\t");
2684     mprintf(fd, "RepeatKey: count = %zu", repeatKeys_.size());
2685     for (const auto &item : repeatKeys_) {
2686         mprintf(fd,
2687             "KeyCode: %d | KeyAction: %s | Times: %d"
2688             "| StatusConfig: %s | StatusConfigValue: %s | BundleName: %s | AbilityName: %s"
2689             "| Action:%s \t", item.keyCode, ConvertKeyActionToString(item.keyAction).c_str(), item.times,
2690             item.statusConfig.c_str(), item.statusConfigValue ? "true" : "false",
2691             item.ability.bundleName.c_str(), item.ability.abilityName.c_str(), item.ability.action.c_str());
2692     }
2693     PrintGestureInfo(fd);
2694 }
2695 
PrintGestureInfo(int32_t fd)2696 void KeyCommandHandler::PrintGestureInfo(int32_t fd)
2697 {
2698     mprintf(fd, "-------------------------- TouchPad Two Fingers Gesture --------------------------\t");
2699     mprintf(fd,
2700         "GestureActive: %s | GestureBundleName: %s | GestureAbilityName: %s"
2701         "| GestureAction: %s \t", twoFingerGesture_.active ? "true" : "false",
2702         twoFingerGesture_.ability.bundleName.c_str(), twoFingerGesture_.ability.abilityName.c_str(),
2703         twoFingerGesture_.ability.action.c_str());
2704     mprintf(fd, "-------------------------- TouchPad Three Fingers Tap Gesture --------------------\t");
2705     mprintf(fd,
2706         "TapBundleName: %s | TapAbilityName: %s"
2707         "| TapAction: %s \t", threeFingersTap_.ability.bundleName.c_str(),
2708         threeFingersTap_.ability.abilityName.c_str(), threeFingersTap_.ability.action.c_str());
2709     mprintf(fd, "-------------------------- Knuckle Single Finger Gesture -------------------------\t");
2710     mprintf(fd,
2711         "GestureState: %s | GestureBundleName: %s | GestureAbilityName: %s"
2712         "| GestureAction: %s \t", singleKnuckleGesture_.state ? "true" : "false",
2713         singleKnuckleGesture_.ability.bundleName.c_str(), singleKnuckleGesture_.ability.abilityName.c_str(),
2714         singleKnuckleGesture_.ability.action.c_str());
2715     mprintf(fd, "-------------------------- Knuckle Two Fingers Gesture ---------------------------\t");
2716     mprintf(fd,
2717         "GestureState: %s | GestureBundleName: %s | GestureAbilityName: %s"
2718         "| GestureAction:%s \t", doubleKnuckleGesture_.state ? "true" : "false",
2719         doubleKnuckleGesture_.ability.bundleName.c_str(), doubleKnuckleGesture_.ability.abilityName.c_str(),
2720         doubleKnuckleGesture_.ability.action.c_str());
2721 }
ConvertKeyActionToString(int32_t keyAction)2722 std::string KeyCommandHandler::ConvertKeyActionToString(int32_t keyAction)
2723 {
2724     static const std::unordered_map<int32_t, std::string> actionMap = {
2725         {0, "UNKNOWN"},
2726         {1, "CANCEL"},
2727         {2, "DOWN"},
2728         {3, "UP"}
2729     };
2730     auto it = actionMap.find(keyAction);
2731     if (it != actionMap.end()) {
2732         return it->second;
2733     } else {
2734         return "UNKNOWN_ACTION";
2735     }
2736 }
operator <<(std::ostream & os,const Sequence & seq)2737 std::ostream& operator<<(std::ostream& os, const Sequence& seq)
2738 {
2739     os << "keys: [";
2740     for (const SequenceKey &singleKey: seq.sequenceKeys) {
2741         os << "(kc:" << singleKey.keyCode << ",ka:" << singleKey.keyAction << ",d:" << singleKey.delay << "),";
2742     }
2743     os << "]: " << seq.ability.bundleName << ":" << seq.ability.abilityName;
2744     return os;
2745 }
2746 
CheckAndUpdateTappingCountAtDown(std::shared_ptr<PointerEvent> touchEvent)2747 void KeyCommandHandler::CheckAndUpdateTappingCountAtDown(std::shared_ptr<PointerEvent> touchEvent)
2748 {
2749     CHKPV(touchEvent);
2750     int64_t currentDownTime = touchEvent->GetActionTime();
2751     int64_t downIntervalTime = currentDownTime - lastDownTime_;
2752     lastDownTime_ = currentDownTime;
2753     if (downIntervalTime <= 0 || downIntervalTime >= TAP_DOWN_INTERVAL_MILLIS) {
2754         tappingCount_ = 1;
2755         return;
2756     }
2757     tappingCount_++;
2758     int64_t timeDiffToPrevKnuckleUpTime = currentDownTime - previousUpTime_;
2759     if (timeDiffToPrevKnuckleUpTime <= downToPrevUpTimeConfig_) {
2760         if (tappingCount_ == MAX_TAP_COUNT) {
2761             DfxHisysevent::ReportFailIfOneSuccTwoFail(touchEvent);
2762         }
2763         if (tappingCount_ > MAX_TAP_COUNT) {
2764             DfxHisysevent::ReportFailIfKnockTooFast();
2765         }
2766     }
2767 }
2768 
TouchPadKnuckleDoubleClickHandle(std::shared_ptr<KeyEvent> event)2769 bool KeyCommandHandler::TouchPadKnuckleDoubleClickHandle(std::shared_ptr<KeyEvent> event)
2770 {
2771     CHKPF(event);
2772     auto actionType = event->GetKeyAction();
2773     if (actionType == KNUCKLE_1F_DOUBLE_CLICK) {
2774         TouchPadKnuckleDoubleClickProcess(PC_PRO_SCREENSHOT_BUNDLE_NAME,
2775             PC_PRO_SCREENSHOT_ABILITY_NAME, "single_knuckle");
2776         return true;
2777     }
2778     if (actionType == KNUCKLE_2F_DOUBLE_CLICK) {
2779         TouchPadKnuckleDoubleClickProcess(PC_PRO_SCREENRECORDER_BUNDLE_NAME,
2780             PC_PRO_SCREENRECORDER_ABILITY_NAME, "double_knuckle");
2781         return true;
2782     }
2783     return false;
2784 }
2785 
TouchPadKnuckleDoubleClickProcess(const std::string bundleName,const std::string abilityName,const std::string action)2786 void KeyCommandHandler::TouchPadKnuckleDoubleClickProcess(const std::string bundleName,
2787     const std::string abilityName, const std::string action)
2788 {
2789     std::string screenStatus = DISPLAY_MONITOR->GetScreenStatus();
2790     bool isScreenLocked = DISPLAY_MONITOR->GetScreenLocked();
2791     if (screenStatus == EventFwk::CommonEventSupport::COMMON_EVENT_SCREEN_OFF || isScreenLocked) {
2792         MMI_HILOGI("The current screen is not in the unlocked state with the screen on");
2793         return;
2794     }
2795     Ability ability;
2796     ability.bundleName = bundleName;
2797     ability.abilityName = abilityName;
2798     ability.params.emplace(std::make_pair("trigger_type", action));
2799     LaunchAbility(ability, NO_DELAY);
2800 }
2801 
ParseLongPressConfig()2802 bool KeyCommandHandler::ParseLongPressConfig()
2803 {
2804     std::string configPath = "/system/variant/phone/base/etc/multimodalinput/universal_drag_app_whitelist.json";
2805     return ParseLongPressJson(configPath);
2806 }
2807 
ParseLongPressJson(const std::string & configFile)2808 bool KeyCommandHandler::ParseLongPressJson(const std::string &configFile)
2809 {
2810     CALL_DEBUG_ENTER;
2811     std::string jsonStr = ReadJsonFile(configFile);
2812     if (jsonStr.empty()) {
2813         MMI_HILOGE("Read configFile failed");
2814         return false;
2815     }
2816     JsonParser parser;
2817     parser.json_ = cJSON_Parse(jsonStr.c_str());
2818     if (!cJSON_IsObject(parser.json_)) {
2819         MMI_HILOGE("Parser.json_ is not object");
2820         return false;
2821     }
2822 
2823     cJSON* item = nullptr;
2824     cJSON* enable = nullptr;
2825     cJSON* status = nullptr;
2826     cJSON_ArrayForEach(item, parser.json_) {
2827         if (!cJSON_IsObject(item)) {
2828             continue;
2829         }
2830         enable = cJSON_GetObjectItem(item, KEY_ENABLE);
2831         status = cJSON_GetObjectItem(item, KEY_STATUS);
2832         if (enable == NULL || status == NULL) {
2833             continue;
2834         }
2835         if (enable->valueint == 1) {
2836             appWhiteList_.insert(item->string);
2837         }
2838     }
2839     return true;
2840 }
2841 
CheckBundleName(const std::shared_ptr<PointerEvent> touchEvent)2842 bool KeyCommandHandler::CheckBundleName(const std::shared_ptr<PointerEvent> touchEvent)
2843 {
2844     CALL_DEBUG_ENTER;
2845     if (!isParseLongPressConfig_) {
2846         MMI_HILOGE("Parse configFile failed");
2847         return false;
2848     }
2849     int32_t windowPid = WIN_MGR->GetWindowPid(touchEvent->GetTargetWindowId());
2850     if (windowPid == RET_ERR) {
2851         MMI_HILOGE("Get window pid failed");
2852         return false;
2853     }
2854 
2855     std::string bundleName;
2856     if (LONG_PRESS_EVENT_HANDLER->GetBundleName(bundleName, windowPid) == RET_ERR) {
2857         MMI_HILOGE("Failed to get bundle name, pid %{public}d", windowPid);
2858         return false;
2859     }
2860     if (appWhiteList_.find(bundleName) == appWhiteList_.end()) {
2861         MMI_HILOGE("The app does not support long-press drag., bundle name:%{public}s", bundleName.c_str());
2862         return false;
2863     }
2864     return true;
2865 }
2866 
OnKunckleSwitchStatusChange(const std::string switchName)2867 void KeyCommandHandler::OnKunckleSwitchStatusChange(const std::string switchName)
2868 {
2869 #ifdef OHOS_BUILD_ENABLE_ANCO
2870     if (switchName != SETTING_KNUCKLE_SWITCH && switchName != SNAPSHOT_KNUCKLE_SWITCH
2871         && switchName != RECORD_KNUCKLE_SWITCH) {
2872         return;
2873     }
2874     bool isKnuckleEnable = !SkipKnuckleDetect();
2875     int32_t ret = WIN_MGR->SyncKnuckleStatus(isKnuckleEnable);
2876     if (ret != RET_OK) {
2877         MMI_HILOGE("sync knuckle status error., ret:%{public}d", ret);
2878     }
2879 #endif // OHOS_BUILD_ENABLE_ANCO
2880 }
2881 } // namespace MMI
2882 } // namespace OHOS
2883