• 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 "accessibility_operator.h"
17 #include "accessibility_system_ability_client.h"
18 
19 namespace OHOS {
20 namespace Accessibility {
21 std::map<int, sptr<IAccessibleAbilityChannel>> AccessibilityOperator::channels_ = {};
22 std::vector<sptr<AccessibilityOperator>>  AccessibilityOperator::instances_ = {};
23 std::recursive_mutex AccessibilityOperator::mutex_ = {};
24 
AccessibilityOperator()25 AccessibilityOperator::AccessibilityOperator()
26 {
27     executeActionResult_ = false;
28 }
29 
~AccessibilityOperator()30 AccessibilityOperator::~AccessibilityOperator()
31 {
32 }
33 
GetInstance()34 AccessibilityOperator &AccessibilityOperator::GetInstance()
35 {
36     std::thread::id tid = std::this_thread::get_id();
37     HILOG_DEBUG("threadId[%{public}u]", (*(uint32_t*)&tid));
38     std::lock_guard<std::recursive_mutex> lock(mutex_);
39     if (instances_.size() >= MAX_INSTANCE) {
40         for (auto iter = instances_.begin(); iter != instances_.end(); iter++) {
41             if (iter->GetRefPtr() != nullptr &&
42                 iter->GetRefPtr()->asyncElementOperatorMng_.GetOperationStatus()) {
43                 HILOG_DEBUG("complete instance is removed");
44                 instances_.erase(iter);
45                 break;
46             }
47         }
48     }
49 
50     HILOG_DEBUG("new instance instanceSize[%{public}u]", instances_.size());
51     sptr<AccessibilityOperator> inst(new AccessibilityOperator());
52     instances_.push_back(inst);
53 
54     HILOG_DEBUG("End instanceSize[%{public}u]", instances_.size());
55     return *(inst.GetRefPtr());
56 }
57 
GetChannel(int channelId)58 sptr<IAccessibleAbilityChannel> AccessibilityOperator::GetChannel(int channelId)
59 {
60     auto channel = channels_.find(channelId);
61     if (channel != channels_.end()) {
62         HILOG_DEBUG("Find aams [channelId:%{public}d]", channelId);
63         return channel->second;
64     } else {
65         HILOG_ERROR("Failed to find aams [channelId:%{public}d]", channelId);
66         return nullptr;
67     }
68 }
69 
AddChannel(const int channelId,const sptr<IAccessibleAbilityChannel> & channel)70 void AccessibilityOperator::AddChannel(const int channelId, const sptr<IAccessibleAbilityChannel> &channel)
71 {
72     HILOG_DEBUG("Add channel to aams [channelId:%{public}d]", channelId);
73     int tempId = *(const_cast<int *>(&channelId));
74     for (auto iter = channels_.begin(); iter != channels_.end(); iter++) {
75         if (iter->first == tempId) {
76             HILOG_ERROR("channel to aams [channelId:%{public}d] is exited", channelId);
77             return;
78         }
79     }
80     sptr<IAccessibleAbilityChannel> tempChanel = const_cast<sptr<IAccessibleAbilityChannel> &>(channel);
81     channels_.insert(std::pair<int, sptr<IAccessibleAbilityChannel>>(tempId, tempChanel));
82 }
83 
RemoveChannel(int channelId)84 void AccessibilityOperator::RemoveChannel(int channelId)
85 {
86     HILOG_DEBUG("Remove channel to aams [channelId:%{public}d]", channelId);
87     auto iter = channels_.find(channelId);
88     if (iter != channels_.end()) {
89         channels_.erase(iter);
90     } else {
91         HILOG_DEBUG("Failed to remove channel with aams [channelId:%{public}d]", channelId);
92     }
93 }
94 
GetRoot(int channelId,AccessibilityElementInfo & elementInfo)95 bool AccessibilityOperator::GetRoot(int channelId, AccessibilityElementInfo &elementInfo)
96 {
97     AccessibilityElementInfo element {};
98     std::vector<AccessibilityElementInfo> elementInfos {};
99     int activeWindow = AccessibilitySystemAbilityClient::GetInstance()->GetActiveWindow();
100     HILOG_DEBUG("activeWindow is %{public}d", activeWindow);
101     bool result = SearchElementInfosByAccessibilityId(channelId, activeWindow, NONE_ID, 0, elementInfos);
102     for (auto& info : elementInfos) {
103         HILOG_DEBUG("element [elementSize:%{public}d]", elementInfosResult_.size());
104         elementInfo = info;
105         break;
106     }
107     return result;
108 }
109 
GetWindows(int channelId)110 std::vector<AccessibilityWindowInfo> AccessibilityOperator::GetWindows(int channelId)
111 {
112     auto channelService = GetChannel(channelId);
113     if (channelService != nullptr) {
114         auto windows = channelService->GetWindows();
115         for (auto &window : windows) {
116             window.SetChannelId(channelId);
117         }
118         return windows;
119     } else {
120         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
121         return windows_;
122     }
123 }
124 
SearchElementInfosByAccessibilityId(int channelId,int accessibilityWindowId,int elementId,int mode,std::vector<AccessibilityElementInfo> & elementInfos)125 bool AccessibilityOperator::SearchElementInfosByAccessibilityId(int channelId,
126     int accessibilityWindowId, int elementId, int mode, std::vector<AccessibilityElementInfo>& elementInfos)
127 {
128     HILOG_DEBUG("[channelId:%{public}d] [windowId:%{public}d]", channelId, accessibilityWindowId);
129     bool result = false;
130     auto channelService = GetChannel(channelId);
131     if (channelService != nullptr) {
132         int sequenceNum = asyncElementOperatorMng_.RecordSearchSequence();
133         HILOG_DEBUG("search element info [channelId:%{public}d] [sequenceNum:%{public}d]",
134             channelId, sequenceNum);
135         result = channelService->SearchElementInfoByAccessibilityId(accessibilityWindowId, elementId, sequenceNum,
136             this, mode);
137         if (!result) {
138             return result;
139         }
140         HILOG_DEBUG("search element info End[channelId:%{public}d] [sequenceNum:%{public}d]",
141             channelId, sequenceNum);
142         if (!asyncElementOperatorMng_.SearchElementResultTimer(sequenceNum)) {
143             HILOG_ERROR("Failed to wait result");
144             result = false;
145             return result;
146         }
147     }
148     HILOG_DEBUG("search element info OK [channelId:%{public}d]", channelId);
149     for (auto& info : elementInfosResult_) {
150         info.SetChannelId(channelId);
151     }
152     asyncElementOperatorMng_.SetOperationStatus(true);
153     HILOG_DEBUG("search element info End[size:%{public}d]", elementInfosResult_.size());
154     elementInfos = elementInfosResult_;
155     return result;
156 }
157 
SearchElementInfosByText(int channelId,int accessibilityWindowId,int elementId,const std::string & text,std::vector<AccessibilityElementInfo> & elementInfos)158 bool AccessibilityOperator::SearchElementInfosByText(int channelId, int accessibilityWindowId,
159     int elementId, const std::string &text, std::vector<AccessibilityElementInfo>& elementInfos)
160 {
161     HILOG_DEBUG("[channelId:%{public}d]", channelId);
162     bool result = false;
163     auto channelService = GetChannel(channelId);
164     if (channelService != nullptr) {
165         int sequenceNum = asyncElementOperatorMng_.RecordSearchSequence();
166         result = channelService->SearchElementInfosByText(accessibilityWindowId, elementId, text, sequenceNum,
167             this);
168         if (!result) {
169             return result;
170         }
171         if (!asyncElementOperatorMng_.SearchElementResultTimer(sequenceNum)) {
172             HILOG_ERROR("Failed to wait result");
173             result = false;
174             return result;
175         }
176     }
177 
178     for (auto& info : elementInfosResult_) {
179         info.SetChannelId(channelId);
180     }
181     asyncElementOperatorMng_.SetOperationStatus(true);
182     HILOG_DEBUG("[size:%{public}d] end", elementInfosResult_.size());
183     elementInfos = elementInfosResult_;
184 
185     return result;
186 }
187 
FindFocusedElementInfo(int channelId,int accessibilityWindowId,int elementId,int focusType,AccessibilityElementInfo & elementInfo)188 bool AccessibilityOperator::FindFocusedElementInfo(int channelId, int accessibilityWindowId,
189     int elementId, int focusType, AccessibilityElementInfo& elementInfo)
190 {
191     HILOG_DEBUG("[channelId:%{public}d]", channelId);
192     bool result = false;
193     auto channelService = GetChannel(channelId);
194     if (channelService != nullptr) {
195         int sequenceNum = asyncElementOperatorMng_.RecordSearchSequence();
196         result = channelService->FindFocusedElementInfo(accessibilityWindowId, elementId,
197             focusType, sequenceNum, this);
198         if (!result) {
199             return result;
200         }
201 
202         HILOG_DEBUG("FindFocusedElementInfo channelId[%{public}d] elementId[%{public}d],\
203             focusType[%{public}d] sequenceNum[%{public}d]",
204             channelId, accessibilityWindowId, elementId, focusType);
205         if (!asyncElementOperatorMng_.SearchElementResultTimer(sequenceNum)) {
206             HILOG_ERROR("Failed to wait result");
207             result = false;
208             return result;
209         }
210     }
211     accessibilityInfoResult_.SetChannelId(channelId);
212     asyncElementOperatorMng_.SetOperationStatus(true);
213     HILOG_DEBUG("[channelId:%{public}d] end", channelId);
214     if ((!accessibilityInfoResult_.GetWindowId()) && (!accessibilityInfoResult_.GetAccessibilityId())) {
215         HILOG_DEBUG("Can't find the component info");
216         result = false;
217     } else {
218         elementInfo = accessibilityInfoResult_;
219         result = true;
220     }
221 
222     return result;
223 }
224 
FocusMoveSearch(int channelId,int accessibilityWindowId,int elementId,int direction,AccessibilityElementInfo & elementInfo)225 bool AccessibilityOperator::FocusMoveSearch(int channelId, int accessibilityWindowId,
226     int elementId, int direction, AccessibilityElementInfo& elementInfo)
227 {
228     HILOG_DEBUG("[channelId:%{public}d]", channelId);
229     bool result = false;
230     auto channelService = GetChannel(channelId);
231     if (channelService != nullptr) {
232         int sequenceNum = asyncElementOperatorMng_.RecordSearchSequence();
233         result = channelService->FocusMoveSearch(accessibilityWindowId, elementId, direction, sequenceNum, this);
234         if (!result) {
235             return result;
236         }
237         if (!asyncElementOperatorMng_.SearchElementResultTimer(sequenceNum)) {
238             HILOG_ERROR("Failed to wait result");
239             result = false;
240             return result;
241         }
242     }
243 
244     accessibilityInfoResult_.SetChannelId(channelId);
245     asyncElementOperatorMng_.SetOperationStatus(true);
246     HILOG_DEBUG("[channelId:%{public}d] end", channelId);
247     elementInfo = accessibilityInfoResult_;
248     if ((!accessibilityInfoResult_.GetWindowId()) && (!accessibilityInfoResult_.GetAccessibilityId())) {
249         HILOG_DEBUG("Can't find the component info");
250         result = false;
251     } else {
252         result = true;
253     }
254     return result;
255 }
256 
ExecuteAction(int channelId,int accessibilityWindowId,int elementId,int action,std::map<std::string,std::string> & actionArguments)257 bool AccessibilityOperator::ExecuteAction(int channelId, int accessibilityWindowId,
258     int elementId, int action,  std::map<std::string, std::string> &actionArguments)
259 {
260     HILOG_DEBUG("[channelId:%{public}d]", channelId);
261     auto channelService = GetChannel(channelId);
262     if (channelService != nullptr) {
263         int sequenceNum = asyncElementOperatorMng_.RecordSearchSequence();
264         bool result = channelService->ExecuteAction(
265             accessibilityWindowId, elementId, action, actionArguments,
266             sequenceNum, this);
267         if (!result) {
268             return result;
269         }
270 
271         if (!asyncElementOperatorMng_.SearchElementResultTimer(sequenceNum)) {
272             HILOG_ERROR("Failed to wait result");
273             return false;
274         }
275     }
276     asyncElementOperatorMng_.SetOperationStatus(true);
277     HILOG_DEBUG("[channelId:%{public}d] end", channelId);
278     return executeActionResult_;
279 }
280 
SetSearchElementInfoByAccessibilityIdResult(const std::vector<AccessibilityElementInfo> & infos,const int sequenceNum)281 void AccessibilityOperator::SetSearchElementInfoByAccessibilityIdResult(
282     const std::vector<AccessibilityElementInfo> &infos, const int sequenceNum)
283 {
284     HILOG_DEBUG("Response[elementInfoSize:%{public}d] [sequenceNum:%{public}d]",
285         infos.size(), sequenceNum);
286     for (auto iter = infos.begin(); iter != infos.end(); iter++) {
287         HILOG_DEBUG("Response");
288         elementInfosResult_.push_back(*iter);
289     }
290     asyncElementOperatorMng_.UpdateSearchFeedback(sequenceNum);
291     HILOG_DEBUG("Response [sequenceNum:%{public}d] end", sequenceNum);
292 }
293 
SetSearchElementInfoByTextResult(const std::vector<AccessibilityElementInfo> & infos,const int sequenceNum)294 void AccessibilityOperator::SetSearchElementInfoByTextResult(const std::vector<AccessibilityElementInfo> &infos,
295     const int sequenceNum)
296 {
297     HILOG_DEBUG("Response [elementInfoSize:%{public}d] [sequenceNum:%{public}d]",
298         infos.size(), sequenceNum);
299     for (auto iter = infos.begin(); iter != infos.end(); iter++) {
300         elementInfosResult_.push_back(*iter);
301     }
302     asyncElementOperatorMng_.UpdateSearchFeedback(sequenceNum);
303     HILOG_DEBUG("Response [sequenceNum:%{public}d] end", sequenceNum);
304 }
305 
SetFindFocusedElementInfoResult(const AccessibilityElementInfo & info,const int sequenceNum)306 void AccessibilityOperator::SetFindFocusedElementInfoResult(const AccessibilityElementInfo &info,
307     const int sequenceNum)
308 {
309     HILOG_DEBUG("Response [sequenceNum:%{public}d]", sequenceNum);
310     accessibilityInfoResult_ = info;
311     asyncElementOperatorMng_.UpdateSearchFeedback(sequenceNum);
312     HILOG_DEBUG("Response [sequenceNum:%{public}d] end", sequenceNum);
313 }
314 
SetFocusMoveSearchResult(const AccessibilityElementInfo & info,const int sequenceNum)315 void AccessibilityOperator::SetFocusMoveSearchResult(const AccessibilityElementInfo &info, const int sequenceNum)
316 {
317     HILOG_DEBUG("Response [sequenceNum:%{public}d]", sequenceNum);
318     accessibilityInfoResult_ = info;
319     asyncElementOperatorMng_.UpdateSearchFeedback(sequenceNum);
320     HILOG_DEBUG("Response [sequenceNum:%{public}d] end", sequenceNum);
321 }
322 
SetExecuteActionResult(const bool succeeded,const int sequenceNum)323 void AccessibilityOperator::SetExecuteActionResult(const bool succeeded, const int sequenceNum)
324 {
325     HILOG_DEBUG("Response [sequenceNum:%{public}d] result[%{public}d]", sequenceNum, succeeded);
326     executeActionResult_ = succeeded;
327     asyncElementOperatorMng_.UpdateSearchFeedback(sequenceNum);
328     HILOG_DEBUG("Response [sequenceNum:%{public}d] end", sequenceNum);
329 }
330 
ExecuteCommonAction(const int channelId,const int action)331 bool AccessibilityOperator::ExecuteCommonAction(const int channelId, const int action)
332 {
333     HILOG_INFO("[channelId:%{public}d]", channelId);
334     auto channelService = GetChannel(channelId);
335     if (channelService != nullptr) {
336         return channelService->ExecuteCommonAction(action);
337     } else {
338         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
339         return false;
340     }
341 }
342 
SetOnKeyPressEventResult(const int channelId,const bool handled,const int sequence)343 void AccessibilityOperator::SetOnKeyPressEventResult(const int channelId, const bool handled, const int sequence)
344 {
345     HILOG_INFO("[channelId:%{public}d]", channelId);
346     auto channelService = GetChannel(channelId);
347     if (channelService != nullptr) {
348         channelService->SetOnKeyPressEventResult(handled, sequence);
349     } else {
350         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
351     }
352 }
353 
GetDisplayResizeScale(const int channelId,const int displayId)354 float AccessibilityOperator::GetDisplayResizeScale(const int channelId, const int displayId)
355 {
356     HILOG_INFO("[channelId:%{public}d]", channelId);
357     auto channelService = GetChannel(channelId);
358     if (channelService != nullptr) {
359         return channelService->GetDisplayResizeScale(displayId);
360     } else {
361         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
362         return 1;
363     }
364 }
365 
GetDisplayResizeCenterX(const int channelId,const int displayId)366 float AccessibilityOperator::GetDisplayResizeCenterX(const int channelId, const int displayId)
367 {
368     HILOG_INFO("[channelId:%{public}d]", channelId);
369     auto channelService = GetChannel(channelId);
370     if (channelService != nullptr) {
371         return channelService->GetDisplayResizeCenterX(displayId);
372     } else {
373         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
374         return 1;
375     }
376 }
377 
GetDisplayResizeCenterY(const int channelId,const int displayId)378 float AccessibilityOperator::GetDisplayResizeCenterY(const int channelId, const int displayId)
379 {
380     HILOG_INFO("[channelId:%{public}d]", channelId);
381     auto channelService = GetChannel(channelId);
382     if (channelService != nullptr) {
383         return channelService->GetDisplayResizeCenterY(displayId);
384     } else {
385         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
386         return 1;
387     }
388 }
389 
GetDisplayResizeRect(const int channelId,const int displayId)390 Rect AccessibilityOperator::GetDisplayResizeRect(const int channelId, const int displayId)
391 {
392     HILOG_INFO("[channelId:%{public}d]", channelId);
393     auto channelService = GetChannel(channelId);
394     if (channelService != nullptr) {
395         return channelService->GetDisplayResizeRect(displayId);
396     } else {
397         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
398         Rect rect {};
399         return rect;
400     }
401 }
402 
ResetDisplayResize(const int channelId,const int displayId,const bool animate)403 bool AccessibilityOperator::ResetDisplayResize(const int channelId, const int displayId, const bool animate)
404 {
405     HILOG_INFO("[channelId:%{public}d]", channelId);
406     auto channelService = GetChannel(channelId);
407     if (channelService != nullptr) {
408         return channelService->ResetDisplayResize(displayId, animate);
409     } else {
410         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
411         return false;
412     }
413 }
414 
SetDisplayResizeScaleAndCenter(const int channelId,const int displayId,const float scale,const float centerX,const float centerY,const bool animate)415 bool AccessibilityOperator::SetDisplayResizeScaleAndCenter(const int channelId,
416     const int displayId, const float scale, const float centerX,
417     const float centerY, const bool animate)
418 {
419     HILOG_INFO("[channelId:%{public}d]", channelId);
420     auto channelService = GetChannel(channelId);
421     if (channelService != nullptr) {
422         return channelService->SetDisplayResizeScaleAndCenter(displayId, scale, centerX,
423             centerY, animate);
424     } else {
425         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
426         return false;
427     }
428 }
429 
SendSimulateGesture(const int channelId,const int sequenceNum,const std::vector<GesturePathDefine> & gestureSteps)430 void AccessibilityOperator::SendSimulateGesture(const int channelId,
431     const int sequenceNum, const std::vector<GesturePathDefine> &gestureSteps)
432 {
433     HILOG_INFO("[channelId:%{public}d]", channelId);
434     auto channelService = GetChannel(channelId);
435     if (channelService != nullptr) {
436         channelService->SendSimulateGesture(sequenceNum, gestureSteps);
437     } else {
438         HILOG_ERROR("Failed to connect to aams [channelId:%{public}d]", channelId);
439     }
440 }
441 } // namespace Accessibility
442 } // namespace OHOS