• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "accessible_ability_channel.h"
17 #include "accessible_ability_manager_service.h"
18 #include "accessibility_window_connection.h"
19 #include "accessibility_window_manager.h"
20 #include "accessible_ability_connection.h"
21 #include "hilog_wrapper.h"
22 #include "transaction/rs_interfaces.h"
23 
24 namespace OHOS {
25 namespace Accessibility {
26 namespace {
27     constexpr int32_t WINDOW_ID_INVALID = -1;
28     constexpr int64_t ELEMENT_ID_INVALID = -1;
29     MMI::InputManager* inputManager_ = MMI::InputManager::GetInstance();
30     std::map<int32_t, std::pair<bool, std::pair<int32_t, int32_t>>> accessibleKeyCodeTable = {
31         {ActionType::ACCESSIBILITY_ACTION_HOME,
32             {false, {MMI::KeyEvent::KEYCODE_META_LEFT, MMI::KeyEvent::KEYCODE_D}}},
33         {ActionType::ACCESSIBILITY_ACTION_RECENTTASK,
34             {false, {MMI::KeyEvent::KEYCODE_META_LEFT, MMI::KeyEvent::KEYCODE_TAB}}},
35         {ActionType::ACCESSIBILITY_ACTION_BACK,
36             {true, {MMI::KeyEvent::KEYCODE_BACK, MMI::KeyEvent::KEYCODE_BACK}}},
37         {ActionType::ACCESSIBILITY_ACTION_NOTIFICATIONCENTER,
38             {true, {MMI::KeyEvent::KEYCODE_CALL_NOTIFICATION_CENTER, MMI::KeyEvent::KEYCODE_CALL_NOTIFICATION_CENTER}}},
39         {ActionType::ACCESSIBILITY_ACTION_CONTROLCENTER,
40             {true, {MMI::KeyEvent::KEYCODE_CALL_CONTROL_CENTER, MMI::KeyEvent::KEYCODE_CALL_CONTROL_CENTER}}}};
41 } // namespace
42 
AccessibleAbilityChannel(const int32_t accountId,const std::string & clientName)43 AccessibleAbilityChannel::AccessibleAbilityChannel(const int32_t accountId, const std::string &clientName)
44     : clientName_(clientName), accountId_(accountId)
45 {
46     eventHandler_ = std::make_shared<AppExecFwk::EventHandler>(
47         Singleton<AccessibleAbilityManagerService>::GetInstance().GetChannelRunner());
48 }
49 
SearchElementInfoByAccessibilityId(const ElementBasicInfo elementBasicInfo,const int32_t requestId,const sptr<IAccessibilityElementOperatorCallback> & callback,const int32_t mode,bool isFilter)50 RetError AccessibleAbilityChannel::SearchElementInfoByAccessibilityId(const ElementBasicInfo elementBasicInfo,
51     const int32_t requestId, const sptr<IAccessibilityElementOperatorCallback> &callback,
52     const int32_t mode, bool isFilter)
53 {
54     int32_t treeId = elementBasicInfo.treeId;
55     int32_t windowId = elementBasicInfo.windowId;
56     int64_t elementId = elementBasicInfo.elementId;
57     HILOG_DEBUG("elementId:%{public}" PRId64 " winId: %{public}d treeId: %{public}d", elementId, windowId, treeId);
58     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
59 
60     if (eventHandler_ == nullptr || callback == nullptr) {
61         HILOG_ERROR("eventHandler_ exist: %{public}d, callback exist: %{public}d.", eventHandler_ != nullptr,
62             callback != nullptr);
63         return RET_ERR_NULLPTR;
64     }
65 
66     int32_t accountId = accountId_;
67     std::string clientName = clientName_;
68     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
69     ffrt::future syncFuture = syncPromise->get_future();
70     eventHandler_->PostTask([accountId, clientName, syncPromise, windowId, elementId, treeId, requestId,
71         callback, mode, isFilter]() {
72         HILOG_DEBUG("search element accountId[%{public}d], name[%{public}s]", accountId, clientName.c_str());
73         sptr<IAccessibilityElementOperator> elementOperator = nullptr;
74         RetError ret = GetElementOperator(accountId, windowId, FOCUS_TYPE_INVALID, clientName,
75             elementOperator, treeId);
76         if (ret != RET_OK || !CheckWinFromAwm(windowId, ret)) {
77             HILOG_ERROR("Get elementOperator failed! accessibilityWindowId[%{public}d]", windowId);
78             std::vector<AccessibilityElementInfo> infos = {};
79             callback->SetSearchElementInfoByAccessibilityIdResult(infos, requestId);
80             syncPromise->set_value(ret);
81             return;
82         }
83 
84         auto& awm = Singleton<AccessibilityWindowManager>::GetInstance();
85         if (windowId == SCENE_BOARD_WINDOW_ID && awm.IsInnerWindowRootElement(elementId)) {
86             std::vector<AccessibilityElementInfo> infos = {};
87             callback->SetSearchElementInfoByAccessibilityIdResult(infos, requestId);
88             HILOG_DEBUG("IsInnerWindowRootElement elementId: %{public}" PRId64 "", elementId);
89         } else {
90             int64_t realElementId = awm.GetSceneBoardElementId(windowId, elementId);
91             Singleton<AccessibleAbilityManagerService>::GetInstance().AddRequestId(windowId, treeId,
92                 requestId, callback);
93             elementOperator->SearchElementInfoByAccessibilityId(realElementId, requestId, callback, mode, isFilter);
94             HILOG_DEBUG("AccessibleAbilityChannel::SearchElementInfoByAccessibilityId successfully");
95         }
96         syncPromise->set_value(RET_OK);
97         }, "SearchElementInfoByAccessibilityId");
98 
99     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
100     if (wait != ffrt::future_status::ready) {
101         HILOG_ERROR("Failed to wait SearchElementInfoByAccessibilityId result");
102         return RET_ERR_TIME_OUT;
103     }
104     return syncFuture.get();
105 }
106 
SearchDefaultFocusedByWindowId(const ElementBasicInfo elementBasicInfo,const int32_t requestId,const sptr<IAccessibilityElementOperatorCallback> & callback,const int32_t mode,bool isFilter)107 RetError AccessibleAbilityChannel::SearchDefaultFocusedByWindowId(const ElementBasicInfo elementBasicInfo,
108     const int32_t requestId, const sptr<IAccessibilityElementOperatorCallback> &callback,
109     const int32_t mode, bool isFilter)
110 {
111     int32_t windowId = elementBasicInfo.windowId;
112     int64_t elementId = elementBasicInfo.elementId;
113     int32_t treeId = elementBasicInfo.treeId;
114     HILOG_DEBUG("elementId:%{public}" PRId64 " winId: %{public}d treeId: %{public}d", elementId, windowId, treeId);
115     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
116 
117     if (eventHandler_ == nullptr || callback == nullptr) {
118         HILOG_ERROR("eventHandler_ exist: %{public}d, callback exist: %{public}d.", eventHandler_ != nullptr,
119             callback != nullptr);
120         return RET_ERR_NULLPTR;
121     }
122 
123     int32_t accountId = accountId_;
124     std::string clientName = clientName_;
125     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
126     ffrt::future syncFuture = syncPromise->get_future();
127     eventHandler_->PostTask([accountId, clientName, syncPromise, windowId, elementId, treeId, requestId,
128         callback, mode, isFilter]() {
129         HILOG_DEBUG("search element accountId[%{public}d], name[%{public}s]", accountId, clientName.c_str());
130         sptr<IAccessibilityElementOperator> elementOperator = nullptr;
131         RetError ret = GetElementOperator(accountId, windowId, FOCUS_TYPE_INVALID, clientName,
132             elementOperator, treeId);
133         if (ret != RET_OK || !CheckWinFromAwm(windowId, ret)) {
134             HILOG_ERROR("Get elementOperator failed! accessibilityWindowId[%{public}d]", windowId);
135             std::vector<AccessibilityElementInfo> infos = {};
136             callback->SetSearchDefaultFocusByWindowIdResult(infos, requestId);
137             syncPromise->set_value(ret);
138             return;
139         }
140 
141         auto& awm = Singleton<AccessibilityWindowManager>::GetInstance();
142         if (windowId == SCENE_BOARD_WINDOW_ID && awm.IsInnerWindowRootElement(elementId)) {
143             std::vector<AccessibilityElementInfo> infos = {};
144             callback->SetSearchDefaultFocusByWindowIdResult(infos, requestId);
145         } else {
146             Singleton<AccessibleAbilityManagerService>::GetInstance().AddRequestId(windowId, treeId,
147                 requestId, callback);
148             elementOperator->SearchDefaultFocusedByWindowId(windowId, requestId, callback, mode, isFilter);
149             HILOG_DEBUG("AccessibleAbilityChannel::SearchElementInfoByAccessibilityId successfully");
150         }
151         syncPromise->set_value(RET_OK);
152         }, "SearchElementInfoByAccessibilityId");
153 
154     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
155     if (wait != ffrt::future_status::ready) {
156         HILOG_ERROR("Failed to wait SearchElementInfoByAccessibilityId result");
157         return RET_ERR_TIME_OUT;
158     }
159     return RET_OK;
160 }
161 
SearchElementInfosByText(const int32_t accessibilityWindowId,const int64_t elementId,const std::string & text,const int32_t requestId,const sptr<IAccessibilityElementOperatorCallback> & callback)162 RetError AccessibleAbilityChannel::SearchElementInfosByText(const int32_t accessibilityWindowId,
163     const int64_t elementId, const std::string &text, const int32_t requestId,
164     const sptr<IAccessibilityElementOperatorCallback> &callback)
165 {
166     HILOG_DEBUG("SearchElementInfosByText :channel SearchElementInfo elementId: %{public}" PRId64 " winId: %{public}d",
167         elementId, accessibilityWindowId);
168     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
169 
170     if (eventHandler_ == nullptr) {
171         HILOG_ERROR("eventHandler_ is nullptr.");
172         return RET_ERR_NULLPTR;
173     }
174     if (callback == nullptr) {
175         HILOG_ERROR("callback is nullptr.");
176         return RET_ERR_NULLPTR;
177     }
178 
179     int32_t treeId = AccessibleAbilityManagerService::GetTreeIdBySplitElementId(elementId);
180     HILOG_DEBUG("SearchElementInfosByText :channel SearchElementInfo treeId: %{public}d", treeId);
181     int32_t accountId = accountId_;
182     std::string clientName = clientName_;
183     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
184     ffrt::future syncFuture = syncPromise->get_future();
185     eventHandler_->PostTask([accountId, clientName, syncPromise, accessibilityWindowId, elementId, treeId, text,
186         requestId, callback]() {
187         HILOG_DEBUG("accountId[%{public}d], name[%{public}s]", accountId, clientName.c_str());
188         sptr<IAccessibilityElementOperator> elementOperator = nullptr;
189         RetError ret = GetElementOperator(accountId, accessibilityWindowId, FOCUS_TYPE_INVALID,
190             clientName, elementOperator, treeId);
191         if (ret != RET_OK) {
192             HILOG_ERROR("Get elementOperator failed! accessibilityWindowId[%{public}d]", accessibilityWindowId);
193             std::vector<AccessibilityElementInfo> infos = {};
194             callback->SetSearchElementInfoByAccessibilityIdResult(infos, requestId);
195             syncPromise->set_value(ret);
196             return;
197         }
198 
199         auto& awm = Singleton<AccessibilityWindowManager>::GetInstance();
200         int64_t realElementId = awm.GetSceneBoardElementId(accessibilityWindowId, elementId);
201         Singleton<AccessibleAbilityManagerService>::GetInstance().AddRequestId(accessibilityWindowId, treeId,
202             requestId, callback);
203         elementOperator->SearchElementInfosByText(realElementId, text, requestId, callback);
204         syncPromise->set_value(RET_OK);
205         }, "SearchElementInfosByText");
206 
207     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
208     if (wait != ffrt::future_status::ready) {
209         HILOG_ERROR("Failed to wait SearchElementInfosByText result");
210         return RET_ERR_TIME_OUT;
211     }
212     return syncFuture.get();
213 }
214 
FindFocusedElementInfo(const int32_t accessibilityWindowId,const int64_t elementId,const int32_t focusType,const int32_t requestId,const sptr<IAccessibilityElementOperatorCallback> & callback)215 RetError AccessibleAbilityChannel::FindFocusedElementInfo(const int32_t accessibilityWindowId,
216     const int64_t elementId, const int32_t focusType, const int32_t requestId,
217     const sptr<IAccessibilityElementOperatorCallback> &callback)
218 {
219     HILOG_DEBUG("channel FindFocusedElementInfo elementId: %{public}" PRId64 " winId: %{public}d",
220         elementId, accessibilityWindowId);
221     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
222 
223     if (eventHandler_== nullptr) {
224         HILOG_ERROR("eventHandler_ is nullptr.");
225         return RET_ERR_NULLPTR;
226     }
227     if (callback == nullptr) {
228         HILOG_ERROR("callback is nullptr.");
229         return RET_ERR_NULLPTR;
230     }
231 
232     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
233     ffrt::future syncFuture = syncPromise->get_future();
234     int32_t treeId = AccessibleAbilityManagerService::GetTreeIdBySplitElementId(elementId);
235     HILOG_DEBUG("FindFocusedElementInfo :channel FindFocusedElementInfo treeId: %{public}d", treeId);
236     int32_t accountId = accountId_;
237     std::string clientName = clientName_;
238     eventHandler_->PostTask([accountId, clientName, syncPromise, accessibilityWindowId, elementId, treeId,
239         focusType, requestId, callback]() {
240         HILOG_DEBUG("accountId[%{public}d], name[%{public}s]", accountId, clientName.c_str());
241         sptr<IAccessibilityElementOperator> elementOperator = nullptr;
242         RetError ret = GetElementOperator(accountId, accessibilityWindowId, focusType,
243             clientName, elementOperator, treeId);
244         if (ret != RET_OK) {
245             HILOG_ERROR("Get elementOperator failed! accessibilityWindowId[%{public}d]", accessibilityWindowId);
246             std::vector<AccessibilityElementInfo> infos = {};
247             callback->SetSearchElementInfoByAccessibilityIdResult(infos, requestId);
248             syncPromise->set_value(ret);
249             return;
250         }
251 
252         auto& awm = Singleton<AccessibilityWindowManager>::GetInstance();
253         int64_t realElementId = awm.GetSceneBoardElementId(accessibilityWindowId, elementId);
254         Singleton<AccessibleAbilityManagerService>::GetInstance().AddRequestId(accessibilityWindowId, treeId,
255             requestId, callback);
256         elementOperator->FindFocusedElementInfo(realElementId, focusType, requestId, callback);
257         syncPromise->set_value(RET_OK);
258         }, "FindFocusedElementInfo");
259 
260     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
261     if (wait != ffrt::future_status::ready) {
262         HILOG_ERROR("Failed to wait FindFocusedElementInfo result");
263         return RET_ERR_TIME_OUT;
264     }
265     return syncFuture.get();
266 }
267 
FocusMoveSearch(const int32_t accessibilityWindowId,const int64_t elementId,const int32_t direction,const int32_t requestId,const sptr<IAccessibilityElementOperatorCallback> & callback)268 RetError AccessibleAbilityChannel::FocusMoveSearch(const int32_t accessibilityWindowId, const int64_t elementId,
269     const int32_t direction, const int32_t requestId, const sptr<IAccessibilityElementOperatorCallback> &callback)
270 {
271     HILOG_DEBUG("FocusMoveSearch :channel FocusMoveSearch elementId: %{public}" PRId64 " winId: %{public}d",
272         elementId, accessibilityWindowId);
273     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
274 
275     if (eventHandler_ == nullptr) {
276         HILOG_ERROR("eventHandler_ is nullptr.");
277         return RET_ERR_NULLPTR;
278     }
279     if (callback == nullptr) {
280         HILOG_ERROR("callback is nullptr.");
281         return RET_ERR_NULLPTR;
282     }
283 
284     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
285     ffrt::future syncFuture = syncPromise->get_future();
286     int32_t treeId = AccessibleAbilityManagerService::GetTreeIdBySplitElementId(elementId);
287     HILOG_DEBUG("FocusMoveSearch :channel FocusMoveSearch treeId: %{public}d", treeId);
288     int32_t accountId = accountId_;
289     std::string clientName = clientName_;
290     eventHandler_->PostTask([accountId, clientName, syncPromise, accessibilityWindowId,
291         elementId, treeId, direction, requestId, callback]() {
292         HILOG_DEBUG("accountId[%{public}d], name[%{public}s]", accountId, clientName.c_str());
293         sptr<IAccessibilityElementOperator> elementOperator = nullptr;
294         RetError ret = GetElementOperator(accountId, accessibilityWindowId, FOCUS_TYPE_INVALID,
295             clientName, elementOperator, treeId);
296         if (ret != RET_OK) {
297             HILOG_ERROR("Get elementOperator failed! accessibilityWindowId[%{public}d]", accessibilityWindowId);
298             std::vector<AccessibilityElementInfo> infos = {};
299             callback->SetSearchElementInfoByAccessibilityIdResult(infos, requestId);
300             syncPromise->set_value(ret);
301             return;
302         }
303 
304         auto& awm = Singleton<AccessibilityWindowManager>::GetInstance();
305         int64_t realElementId = awm.GetSceneBoardElementId(accessibilityWindowId, elementId);
306         Singleton<AccessibleAbilityManagerService>::GetInstance().AddRequestId(accessibilityWindowId, treeId,
307             requestId, callback);
308         elementOperator->FocusMoveSearch(realElementId, direction, requestId, callback);
309         syncPromise->set_value(RET_OK);
310         }, "FocusMoveSearch");
311 
312     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
313     if (wait != ffrt::future_status::ready) {
314         HILOG_ERROR("Failed to wait FocusMoveSearch result");
315         return RET_ERR_TIME_OUT;
316     }
317     return syncFuture.get();
318 }
319 
SetKeyCodeToMmi(std::shared_ptr<MMI::KeyEvent> & keyEvent,const bool isPress,const int32_t keyCode)320 void AccessibleAbilityChannel::SetKeyCodeToMmi(std::shared_ptr<MMI::KeyEvent>& keyEvent, const bool isPress,
321     const int32_t keyCode)
322 {
323     HILOG_DEBUG();
324     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
325     if (keyEvent == nullptr) {
326         HILOG_ERROR("KeyEvent is nullptr");
327         return;
328     }
329     MMI::KeyEvent::KeyItem item;
330     item.SetPressed(isPress);
331     item.SetKeyCode(keyCode);
332     keyEvent->AddKeyItem(item);
333     keyEvent->SetKeyCode(keyCode);
334 }
335 
TransmitActionToMmi(const int32_t action)336 RetError AccessibleAbilityChannel::TransmitActionToMmi(const int32_t action)
337 {
338     HILOG_DEBUG("The action is %{public}d", action);
339     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
340     std::shared_ptr<MMI::KeyEvent> keyEventUp = MMI::KeyEvent::Create();
341     std::shared_ptr<MMI::KeyEvent> keyEventDown = MMI::KeyEvent::Create();
342     if (keyEventUp == nullptr || keyEventDown == nullptr) {
343         HILOG_ERROR("KeyEvent is nullptr");
344         return RET_ERR_NULLPTR;
345     }
346 
347     if (!inputManager_) {
348         HILOG_ERROR("inputManager_ is nullptr");
349         return RET_ERR_NULLPTR;
350     }
351 
352     HILOG_INFO("Transmit keycode to MMI");
353 
354     if (accessibleKeyCodeTable.at(action).first) {
355         SetKeyCodeToMmi(keyEventDown, true, accessibleKeyCodeTable.at(action).second.first);
356         SetKeyCodeToMmi(keyEventUp, false, accessibleKeyCodeTable.at(action).second.first);
357     } else {
358         SetKeyCodeToMmi(keyEventDown, true, accessibleKeyCodeTable.at(action).second.first);
359         SetKeyCodeToMmi(keyEventUp, false, accessibleKeyCodeTable.at(action).second.first);
360         SetKeyCodeToMmi(keyEventDown, true, accessibleKeyCodeTable.at(action).second.second);
361     }
362     keyEventDown->SetKeyAction(MMI::KeyEvent::KEY_ACTION_DOWN);
363     keyEventUp->SetKeyAction(MMI::KeyEvent::KEY_ACTION_UP);
364     inputManager_->SimulateInputEvent(keyEventDown);
365     inputManager_->SimulateInputEvent(keyEventUp);
366 
367     return RET_OK;
368 }
369 
EnableScreenCurtain(bool isEnable)370 RetError AccessibleAbilityChannel::EnableScreenCurtain(bool isEnable)
371 {
372     HILOG_DEBUG();
373     auto& aams = Singleton<AccessibleAbilityManagerService>::GetInstance();
374     aams.PostDelayUnloadTask();
375     return aams.SetCurtainScreenUsingStatus(isEnable);
376 }
377 
ExecuteAction(const int32_t accessibilityWindowId,const int64_t elementId,const int32_t action,const std::map<std::string,std::string> & actionArguments,const int32_t requestId,const sptr<IAccessibilityElementOperatorCallback> & callback)378 RetError AccessibleAbilityChannel::ExecuteAction(const int32_t accessibilityWindowId, const int64_t elementId,
379     const int32_t action, const std::map<std::string, std::string> &actionArguments, const int32_t requestId,
380     const sptr<IAccessibilityElementOperatorCallback> &callback)
381 {
382     HILOG_DEBUG("ExecuteAction elementId:%{public}" PRId64 " winId:%{public}d, action:%{public}d, requestId:%{public}d",
383         elementId, accessibilityWindowId, action, requestId);
384     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
385     if (eventHandler_ == nullptr || callback == nullptr) {
386         HILOG_ERROR("eventHandler_ exist: %{public}d, callback exist: %{public}d.", eventHandler_ != nullptr,
387             callback != nullptr);
388         return RET_ERR_NULLPTR;
389     }
390 
391     if (accessibleKeyCodeTable.find(action) != accessibleKeyCodeTable.end()) {
392         RetError ret = TransmitActionToMmi(action);
393         if (ret != RET_OK) {
394             HILOG_ERROR("Transmit Action To Mmi failed!");
395             callback->SetExecuteActionResult(false, requestId);
396             return RET_ERR_FAILED;
397         }
398         callback->SetExecuteActionResult(true, requestId);
399         return RET_OK;
400     }
401     SetFocusWindowIdAndElementId(accessibilityWindowId, elementId, action);
402     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
403     ffrt::future syncFuture = syncPromise->get_future();
404     int32_t treeId = AccessibleAbilityManagerService::GetTreeIdBySplitElementId(elementId);
405     int32_t accountId = accountId_;
406     std::string clientName = clientName_;
407     eventHandler_->PostTask([accountId, clientName, syncPromise, accessibilityWindowId, elementId, treeId, action,
408         actionArguments, requestId, callback]() {
409         sptr<IAccessibilityElementOperator> elementOperator = nullptr;
410         RetError ret = GetElementOperator(accountId, accessibilityWindowId, FOCUS_TYPE_INVALID, clientName,
411             elementOperator, treeId);
412         if (ret != RET_OK) {
413             HILOG_ERROR("Get elementOperator failed! accessibilityWindowId[%{public}d]", accessibilityWindowId);
414             syncPromise->set_value(ret);
415             return;
416         }
417 
418         auto& awm = Singleton<AccessibilityWindowManager>::GetInstance();
419         int64_t realElementId = awm.GetSceneBoardElementId(accessibilityWindowId, elementId);
420         Singleton<AccessibleAbilityManagerService>::GetInstance().AddRequestId(accessibilityWindowId, treeId,
421             requestId, callback);
422         elementOperator->ExecuteAction(realElementId, action, actionArguments, requestId, callback);
423         syncPromise->set_value(RET_OK);
424         }, "ExecuteAction");
425 
426     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
427     if (wait != ffrt::future_status::ready) {
428         HILOG_ERROR("Failed to wait ExecuteAction result");
429         return RET_ERR_TIME_OUT;
430     }
431     return syncFuture.get();
432 }
433 
SetFocusWindowIdAndElementId(const int32_t accessibilityWindowId,const int64_t elementId,const int32_t action)434 void AccessibleAbilityChannel::SetFocusWindowIdAndElementId(const int32_t accessibilityWindowId,
435     const int64_t elementId, const int32_t action)
436 {
437     auto& awm = Singleton<AccessibleAbilityManagerService>::GetInstance();
438     if ((action == ActionType::ACCESSIBILITY_ACTION_ACCESSIBILITY_FOCUS)) {
439         awm.SetFocusWindowId(accessibilityWindowId);
440         awm.SetFocusElementId(elementId);
441     } else if (action == ActionType::ACCESSIBILITY_ACTION_CLEAR_ACCESSIBILITY_FOCUS) {
442         awm.SetFocusWindowId(WINDOW_ID_INVALID);
443         awm.SetFocusElementId(ELEMENT_ID_INVALID);
444     }
445 }
446 
GetWindow(const int32_t windowId,AccessibilityWindowInfo & windowInfo)447 RetError AccessibleAbilityChannel::GetWindow(const int32_t windowId, AccessibilityWindowInfo &windowInfo)
448 {
449     HILOG_DEBUG("windowId:%{public}d", windowId);
450     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
451     if (eventHandler_== nullptr) {
452         HILOG_ERROR("eventHandler_ is nullptr.");
453         return RET_ERR_NULLPTR;
454     }
455 
456     int32_t accountId = accountId_;
457     std::string clientName = clientName_;
458     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
459     std::shared_ptr<AccessibilityWindowInfo> tmpWindowInfo = std::make_shared<AccessibilityWindowInfo>(windowInfo);
460     ffrt::future syncFuture = syncPromise->get_future();
461     eventHandler_->PostTask([accountId, clientName, windowId, tmpWindowInfo, syncPromise]() {
462         HILOG_DEBUG("windowId:%{public}d", windowId);
463         sptr<AccessibleAbilityConnection> clientConnection = GetConnection(accountId, clientName);
464         if (!clientConnection) {
465             HILOG_ERROR("There is no client connection");
466             syncPromise->set_value(RET_ERR_NO_CONNECTION);
467             return;
468         }
469         if (!(clientConnection->GetAbilityInfo().GetCapabilityValues() & Capability::CAPABILITY_RETRIEVE)) {
470             HILOG_ERROR("AccessibleAbilityChannel::GetWindow failed: no capability");
471             syncPromise->set_value(RET_ERR_NO_CAPABILITY);
472             return;
473         }
474 
475         if (Singleton<AccessibilityWindowManager>::GetInstance().GetAccessibilityWindow(windowId, *tmpWindowInfo)) {
476             syncPromise->set_value(RET_OK);
477         } else {
478             syncPromise->set_value(RET_ERR_NO_WINDOW_CONNECTION);
479         }
480         }, "GetWindow");
481 
482     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
483     if (wait != ffrt::future_status::ready) {
484         HILOG_ERROR("Failed to wait GetWindow result");
485         return RET_ERR_TIME_OUT;
486     }
487 
488     windowInfo = *tmpWindowInfo;
489     return syncFuture.get();
490 }
491 
GetWindows(std::vector<AccessibilityWindowInfo> & windows)492 RetError AccessibleAbilityChannel::GetWindows(std::vector<AccessibilityWindowInfo> &windows)
493 {
494     HILOG_DEBUG();
495     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
496 #ifdef OHOS_BUILD_ENABLE_DISPLAY_MANAGER
497     uint64_t displayId = Singleton<AccessibilityDisplayManager>::GetInstance().GetDefaultDisplayId();
498     HILOG_DEBUG("default display id is %{public}" PRIu64 "", displayId);
499     return GetWindows(displayId, windows);
500 #else
501     HILOG_DEBUG("not support display manager");
502     return GetWindows(0, windows);
503 #endif
504 }
505 
GetWindowsByDisplayId(const uint64_t displayId,std::vector<AccessibilityWindowInfo> & windows)506 RetError AccessibleAbilityChannel::GetWindowsByDisplayId(const uint64_t displayId,
507     std::vector<AccessibilityWindowInfo> &windows)
508 {
509     HILOG_DEBUG();
510     return GetWindows(displayId, windows);
511 }
512 
GetWindows(uint64_t displayId,std::vector<AccessibilityWindowInfo> & windows) const513 RetError AccessibleAbilityChannel::GetWindows(uint64_t displayId, std::vector<AccessibilityWindowInfo> &windows) const
514 {
515     if (eventHandler_== nullptr) {
516         HILOG_ERROR("eventHandler_ is nullptr.");
517         return RET_ERR_NULLPTR;
518     }
519 
520     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
521     auto tmpWindows = std::make_shared<std::vector<AccessibilityWindowInfo>>(windows);
522     int32_t accountId = accountId_;
523     std::string clientName = clientName_;
524     ffrt::future syncFuture = syncPromise->get_future();
525     eventHandler_->PostTask([accountId, clientName, displayId, tmpWindows, syncPromise]() {
526         HILOG_DEBUG();
527         sptr<AccessibleAbilityConnection> clientConnection = GetConnection(accountId, clientName);
528         if (!clientConnection) {
529             HILOG_ERROR("There is no client connection");
530             syncPromise->set_value(RET_ERR_NO_CONNECTION);
531             return;
532         }
533 
534         if (!(clientConnection->GetAbilityInfo().GetCapabilityValues() & Capability::CAPABILITY_RETRIEVE)) {
535             HILOG_ERROR("GetWindows failed: no capability");
536             syncPromise->set_value(RET_ERR_NO_CAPABILITY);
537             return;
538         }
539 
540         std::vector<AccessibilityWindowInfo> windowInfos =
541             Singleton<AccessibilityWindowManager>::GetInstance().GetAccessibilityWindows();
542 #ifdef OHOS_BUILD_ENABLE_DISPLAY_MANAGER
543         for (auto &window : windowInfos) {
544             if (window.GetDisplayId() == displayId) {
545                 tmpWindows->emplace_back(window);
546             }
547         }
548 #else
549         for (auto &window : windowInfos) {
550             tmpWindows->emplace_back(window);
551         }
552 #endif
553         syncPromise->set_value(RET_OK);
554         }, "GetWindows");
555 
556     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
557     if (wait != ffrt::future_status::ready) {
558         HILOG_ERROR("Failed to wait GetWindows result");
559         return RET_ERR_TIME_OUT;
560     }
561 
562     windows = *tmpWindows;
563     return syncFuture.get();
564 }
565 
SetOnKeyPressEventResult(const bool handled,const int32_t sequence)566 void AccessibleAbilityChannel::SetOnKeyPressEventResult(const bool handled, const int32_t sequence)
567 {
568     HILOG_DEBUG();
569     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
570     if (eventHandler_== nullptr) {
571         HILOG_ERROR("eventHandler_ is nullptr.");
572         return;
573     }
574 
575     int32_t accountId = accountId_;
576     std::string clientName = clientName_;
577     eventHandler_->PostTask([accountId, clientName, handled, sequence]() {
578         sptr<KeyEventFilter> keyEventFilter =
579             Singleton<AccessibleAbilityManagerService>::GetInstance().GetKeyEventFilter();
580         if (!keyEventFilter) {
581             return;
582         }
583 
584         sptr<AccessibleAbilityConnection> clientConnection = GetConnection(accountId, clientName);
585         if (!clientConnection) {
586             HILOG_ERROR("There is no client connection");
587             return;
588         }
589         keyEventFilter->SetServiceOnKeyEventResult(*clientConnection, handled, sequence);
590         }, "SetOnKeyPressEventResult");
591 }
592 
GetCursorPosition(const int32_t accessibilityWindowId,const int64_t elementId,const int32_t requestId,const sptr<IAccessibilityElementOperatorCallback> & callback)593 RetError AccessibleAbilityChannel::GetCursorPosition(const int32_t accessibilityWindowId, const int64_t elementId,
594     const int32_t requestId, const sptr<IAccessibilityElementOperatorCallback> &callback)
595 {
596     HILOG_DEBUG("GetCursorPosition :channel GetCursorPosition elementId: %{public}" PRId64 " winId: %{public}d",
597         elementId, accessibilityWindowId);
598     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
599     if (eventHandler_== nullptr) {
600         HILOG_ERROR("eventHandler_ is nullptr.");
601         return RET_ERR_NULLPTR;
602     }
603     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
604     ffrt::future syncFuture = syncPromise->get_future();
605     int32_t treeId = AccessibleAbilityManagerService::GetTreeIdBySplitElementId(elementId);
606     HILOG_DEBUG("GetCursorPosition :channel GetCursorPosition treeId: %{public}d", treeId);
607     int32_t accountId = accountId_;
608     std::string clientName = clientName_;
609     eventHandler_->PostTask([accountId, clientName, syncPromise, accessibilityWindowId, elementId, treeId,
610         requestId, callback]() {
611         HILOG_DEBUG("accountId[%{public}d], name[%{public}s]", accountId, clientName.c_str());
612         sptr<IAccessibilityElementOperator> elementOperator = nullptr;
613         RetError ret = GetElementOperator(accountId, accessibilityWindowId, FOCUS_TYPE_INVALID, clientName,
614             elementOperator, treeId);
615         if (ret != RET_OK) {
616             HILOG_ERROR("Get elementOperator failed! accessibilityWindowId[%{public}d]", accessibilityWindowId);
617             syncPromise->set_value(ret);
618             return;
619         }
620 
621         auto& awm = Singleton<AccessibilityWindowManager>::GetInstance();
622         int64_t realElementId = awm.GetSceneBoardElementId(accessibilityWindowId, elementId);
623         Singleton<AccessibleAbilityManagerService>::GetInstance().AddRequestId(accessibilityWindowId, treeId,
624             requestId, callback);
625         elementOperator->GetCursorPosition(realElementId, requestId, callback);
626         syncPromise->set_value(RET_OK);
627         }, "GetCursorPosition");
628 
629     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
630     if (wait != ffrt::future_status::ready) {
631         HILOG_ERROR("Failed to wait GetCursorPosition result");
632         return RET_ERR_TIME_OUT;
633     }
634     return syncFuture.get();
635 }
636 
SendSimulateGesture(const std::shared_ptr<AccessibilityGestureInjectPath> & gesturePath)637 RetError AccessibleAbilityChannel::SendSimulateGesture(
638     const std::shared_ptr<AccessibilityGestureInjectPath>& gesturePath)
639 {
640     HILOG_INFO();
641     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
642     if (eventHandler_== nullptr) {
643         HILOG_ERROR("eventHandler_ is nullptr");
644         return RET_ERR_NULLPTR;
645     }
646 
647     int32_t accountId = accountId_;
648     std::string clientName = clientName_;
649     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
650     ffrt::future syncFuture = syncPromise->get_future();
651     eventHandler_->PostTask([accountId, clientName, gesturePath, syncPromise]() {
652         HILOG_DEBUG();
653         sptr<AccessibleAbilityConnection> clientConnection = GetConnection(accountId, clientName);
654         if (!clientConnection) {
655             HILOG_ERROR("There is no client connection");
656             syncPromise->set_value(RET_ERR_NO_CONNECTION);
657             return;
658         }
659 
660         if (!(clientConnection->GetAbilityInfo().GetCapabilityValues() & Capability::CAPABILITY_GESTURE)) {
661             HILOG_ERROR("AccessibleAbilityChannel::SendSimulateGesture failed: no capability");
662             syncPromise->set_value(RET_ERR_NO_CAPABILITY);
663             return;
664         }
665 
666         sptr<TouchEventInjector> touchEventInjector =
667             Singleton<AccessibleAbilityManagerService>::GetInstance().GetTouchEventInjector();
668         if (!touchEventInjector) {
669             HILOG_ERROR("touchEventInjector is null");
670             syncPromise->set_value(RET_ERR_NO_INJECTOR);
671             return;
672         }
673         touchEventInjector->InjectEvents(gesturePath);
674         syncPromise->set_value(RET_OK);
675         }, "SendSimulateGesture");
676 
677     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
678     if (wait != ffrt::future_status::ready) {
679         HILOG_ERROR("Failed to wait SendSimulateGesture result");
680         return RET_ERR_TIME_OUT;
681     }
682     return syncFuture.get();
683 }
684 
SetTargetBundleName(const std::vector<std::string> & targetBundleNames)685 RetError AccessibleAbilityChannel::SetTargetBundleName(const std::vector<std::string> &targetBundleNames)
686 {
687     HILOG_DEBUG();
688     Singleton<AccessibleAbilityManagerService>::GetInstance().PostDelayUnloadTask();
689     if (eventHandler_== nullptr) {
690         HILOG_ERROR("eventHandler_ is nullptr");
691         return RET_ERR_NULLPTR;
692     }
693 
694     int32_t accountId = accountId_;
695     std::string clientName = clientName_;
696     std::shared_ptr<ffrt::promise<RetError>> syncPromise = std::make_shared<ffrt::promise<RetError>>();
697     ffrt::future syncFuture = syncPromise->get_future();
698     eventHandler_->PostTask([accountId, clientName, targetBundleNames, syncPromise]() {
699         HILOG_DEBUG();
700         sptr<AccessibleAbilityConnection> clientConnection = GetConnection(accountId, clientName);
701         if (!clientConnection) {
702             HILOG_ERROR("There is no client connection");
703             syncPromise->set_value(RET_ERR_NO_CONNECTION);
704             return;
705         }
706 
707         clientConnection->SetAbilityInfoTargetBundleName(targetBundleNames);
708         syncPromise->set_value(RET_OK);
709         }, "SetTargetBundleName");
710 
711     ffrt::future_status wait = syncFuture.wait_for(std::chrono::milliseconds(TIME_OUT_OPERATOR));
712     if (wait != ffrt::future_status::ready) {
713         HILOG_ERROR("Failed to wait SetTargetBundleName result");
714         return RET_ERR_TIME_OUT;
715     }
716     return syncFuture.get();
717 }
718 
GetConnection(int32_t accountId,const std::string & clientName)719 sptr<AccessibleAbilityConnection> AccessibleAbilityChannel::GetConnection(
720     int32_t accountId, const std::string &clientName)
721 {
722     HILOG_DEBUG();
723     sptr<AccessibilityAccountData> accountData =
724         Singleton<AccessibleAbilityManagerService>::GetInstance().GetAccountData(accountId);
725     if (accountData == nullptr) {
726         HILOG_ERROR("accountData is nullptr");
727         return nullptr;
728     }
729 
730     HILOG_DEBUG("accountId[%{public}d] clientName[%{public}s]", accountId, clientName.c_str());
731     return accountData->GetAccessibleAbilityConnection(clientName);
732 }
733 
GetElementOperator(int32_t accountId,int32_t windowId,int32_t focusType,const std::string & clientName,sptr<IAccessibilityElementOperator> & elementOperator,const int32_t treeId)734 RetError AccessibleAbilityChannel::GetElementOperator(
735     int32_t accountId, int32_t windowId, int32_t focusType, const std::string &clientName,
736     sptr<IAccessibilityElementOperator> &elementOperator, const int32_t treeId)
737 {
738     HILOG_DEBUG();
739     elementOperator = nullptr;
740     sptr<AccessibleAbilityConnection> clientConnection = GetConnection(accountId, clientName);
741     if (!clientConnection) {
742         HILOG_ERROR("There is no client connection");
743         return RET_ERR_NO_CONNECTION;
744     }
745     if (!(clientConnection->GetAbilityInfo().GetCapabilityValues() & Capability::CAPABILITY_RETRIEVE)) {
746         HILOG_ERROR("the client has no retieve capability");
747         return RET_ERR_NO_CAPABILITY;
748     }
749 
750     sptr<AccessibilityAccountData> accountData =
751         Singleton<AccessibleAbilityManagerService>::GetInstance().GetAccountData(accountId);
752     if (!accountData) {
753         HILOG_ERROR("accountData is nullptr");
754         return RET_ERR_NULLPTR;
755     }
756     int32_t realId = Singleton<AccessibilityWindowManager>::GetInstance().ConvertToRealWindowId(windowId, focusType);
757     sptr<AccessibilityWindowConnection> connection =  nullptr;
758     connection = accountData->GetAccessibilityWindowConnection(realId);
759     if (connection == nullptr) {
760         HILOG_ERROR("windowId[%{public}d] has no connection", realId);
761         return RET_ERR_NO_WINDOW_CONNECTION;
762     }
763     if (treeId <= 0) {
764         elementOperator = connection->GetProxy();
765     } else {
766         elementOperator = connection->GetCardProxy(treeId);
767     }
768     if (!elementOperator) {
769         HILOG_ERROR("The proxy of window connection is nullptr");
770         return RET_ERR_NULLPTR;
771     }
772     return RET_OK;
773 }
774 
CheckWinFromAwm(const int32_t windowId,const int32_t getElementOperatorResult)775 bool AccessibleAbilityChannel::CheckWinFromAwm(const int32_t windowId, const int32_t getElementOperatorResult)
776 {
777     HILOG_DEBUG("CheckWinFromAwm window: %{public}d, ConnectResult: [%{public}d]", windowId, getElementOperatorResult);
778     if (windowId == SCENE_BOARD_WINDOW_ID && getElementOperatorResult == RET_OK) {
779         return true;
780     }
781     std::vector<AccessibilityWindowInfo> windows =
782         Singleton<AccessibilityWindowManager>::GetInstance().GetAccessibilityWindows();
783     if (!windows.empty()) {
784         for (const auto& window: windows) {
785             if (windowId == window.GetWindowId()) {
786                 return true;
787             }
788         }
789     }
790     return false;
791 }
792 } // namespace Accessibility
793 } // namespace OHOS