* Copyright (C) 2022-2025 Huawei Device Co., Ltd.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "accessible_ability_manager.h"
#include "hilog_wrapper.h"
#include "utils.h"
namespace OHOS {
namespace Accessibility {
namespace {
const std::string SCREEN_READER_BUNDLE_NAME = "com.ohos.hmos.screenreader";
}
AccessibleAbilityManager::~AccessibleAbilityManager()
{
connectedA11yAbilities_.Clear();
connectingA11yAbilities_.Clear();
waitDisconnectA11yAbilities_.Clear();
appStateObserverAbilities_.Clear();
}
void AccessibleAbilityManager::Clear()
{
connectedA11yAbilities_.Clear();
enabledAbilities_.clear();
}
void AccessibleAbilityManager::AddConnectedAbility(sptr<AccessibleAbilityConnection>& connection)
{
if (!connection) {
HILOG_ERROR("connection is nullptr");
return;
}
std::string uri = Utils::GetUri(connection->GetElementName());
connectedA11yAbilities_.AddAccessibilityAbility(uri, connection);
}
void AccessibleAbilityManager::RemoveConnectedAbility(const AppExecFwk::ElementName &element)
{
connectedA11yAbilities_.RemoveAccessibilityAbilityByUri(Utils::GetUri(element));
}
void AccessibleAbilityManager::RemoveConnectedAbilityByUri(const std::string &uri)
{
connectedA11yAbilities_.RemoveAccessibilityAbilityByUri(uri);
}
void AccessibleAbilityManager::RemoveConnectedAbilityByName(const std::string &bundleName, bool& result)
{
connectedA11yAbilities_.RemoveAccessibilityAbilityByName(bundleName, result);
}
sptr<AccessibleAbilityConnection> AccessibleAbilityManager::GetConnectedAbilityByName(const std::string &elementName)
{
return connectedA11yAbilities_.GetAccessibilityAbilityByName(elementName);
}
void AccessibleAbilityManager::GetConnectedAbilities(std::vector<sptr<AccessibleAbilityConnection>>& connectionList)
{
connectedA11yAbilities_.GetAccessibilityAbilities(connectionList);
}
void AccessibleAbilityManager::GetConnectedAbilitiesInfo(std::vector<AccessibilityAbilityInfo>& abilities)
{
connectedA11yAbilities_.GetAbilitiesInfo(abilities);
}
void AccessibleAbilityManager::GetConnectedAbilitiesMap(
std::map<std::string, sptr<AccessibleAbilityConnection>> &connectionMap)
{
connectedA11yAbilities_.GetAccessibilityAbilitiesMap(connectionMap);
}
void AccessibleAbilityManager::ClearConnectedAbilities()
{
connectedA11yAbilities_.Clear();
}
size_t AccessibleAbilityManager::GetConnectedAbilitiesSize()
{
return connectedA11yAbilities_.GetSize();
}
void AccessibleAbilityManager::AddConnectingAbility(
const std::string &uri, const sptr<AccessibleAbilityConnection> &connection)
{
connectingA11yAbilities_.AddAccessibilityAbility(uri, connection);
}
void AccessibleAbilityManager::RemoveConnectingAbility(const std::string &uri)
{
connectingA11yAbilities_.RemoveAccessibilityAbilityByUri(uri);
}
sptr<AccessibleAbilityConnection> AccessibleAbilityManager::GetConnectingAbility(const std::string &uri)
{
return connectingA11yAbilities_.GetAccessibilityAbilityByUri(uri);
}
size_t AccessibleAbilityManager::GetConnectingAbilitiesSize()
{
return connectingA11yAbilities_.GetSize();
}
void AccessibleAbilityManager::AddWaitDisconnectAbility(sptr<AccessibleAbilityConnection>& connection)
{
HILOG_INFO();
if (!connection) {
HILOG_ERROR("connection is nullptr");
return;
}
if (connection->GetIsRegisterDisconnectCallback()) {
HILOG_INFO();
std::string uri = Utils::GetUri(connection->GetElementName());
waitDisconnectA11yAbilities_.AddAccessibilityAbility(uri, connection);
}
}
void AccessibleAbilityManager::RemoveWaitDisconnectAbility(const std::string &uri)
{
HILOG_INFO();
waitDisconnectA11yAbilities_.RemoveAccessibilityAbilityByUri(uri);
}
const sptr<AccessibleAbilityConnection> AccessibleAbilityManager::GetWaitDisConnectAbility(
const std::string &elementName)
{
return waitDisconnectA11yAbilities_.GetAccessibilityAbilityByName(elementName);
}
size_t AccessibleAbilityManager::GetWaitDisconnectAbilitiesSize()
{
return waitDisconnectA11yAbilities_.GetSize();
}
void AccessibleAbilityManager::AddAppStateObserverAbility(
const std::string &uri, const sptr<AccessibleAbilityConnection> &connection)
{
if (uri.empty() || !connection) {
HILOG_ERROR("Invalid parameters for AddAppStateObserverAbility");
return;
}
appStateObserverAbilities_.AddAccessibilityAbility(uri, connection);
}
void AccessibleAbilityManager::RemoveAppStateObserverAbility(const std::string& uri)
{
if (uri.empty()) {
HILOG_ERROR("Invalid uri for RemoveAppStateObserverAbility");
return;
}
appStateObserverAbilities_.RemoveAccessibilityAbilityByUri(uri);
}
sptr<AccessibleAbilityConnection> AccessibleAbilityManager::GetAppStateObserverAbility(const std::string& uri)
{
return appStateObserverAbilities_.GetAccessibilityAbilityByUri(uri);
}
void AccessibleAbilityManager::AddEnabledAbility(const std::string &name)
{
HILOG_DEBUG("AddEnabledAbility start.");
if (std::any_of(enabledAbilities_.begin(), enabledAbilities_.end(),
[name](const std::string &abilityName) {
return abilityName == name;
})) {
HILOG_DEBUG("The ability is already enabled, and it's name is %{public}s", name.c_str());
return;
}
enabledAbilities_.push_back(name);
UpdateEnableAbilityListsState();
HILOG_DEBUG("Add EnabledAbility: %{public}zu", enabledAbilities_.size());
}
RetError AccessibleAbilityManager::RemoveEnabledAbility(const std::string &name)
{
HILOG_DEBUG("RemoveEnabledAbility start");
for (auto it = enabledAbilities_.begin(); it != enabledAbilities_.end(); it++) {
if (*it == name) {
HILOG_DEBUG("Removed %{public}s from EnabledAbility: ", name.c_str());
enabledAbilities_.erase(it);
UpdateEnableAbilityListsState();
HILOG_DEBUG("EnabledAbility size %{public}zu", enabledAbilities_.size());
return RET_OK;
}
}
HILOG_ERROR("The ability %{public}s is not enabled.", name.c_str());
return RET_ERR_NOT_ENABLED;
}
const std::vector<std::string> &AccessibleAbilityManager::GetEnabledAbilities() const
{
HILOG_DEBUG("enabledAbilities_'s size is (%{public}zu).", enabledAbilities_.size());
for (auto& ability : enabledAbilities_) {
HILOG_DEBUG("bundleName is %{public}s ", ability.c_str());
}
return enabledAbilities_;
}
void AccessibleAbilityManager::AddInstalledAbility(AccessibilityAbilityInfo& abilityInfo)
{
HILOG_DEBUG("abilityInfo's bundle name is %{public}s", abilityInfo.GetPackageName().c_str());
for (size_t i = 0; i < installedAbilities_.size(); i++) {
if ((installedAbilities_[i].GetPackageName() == abilityInfo.GetPackageName()) &&
installedAbilities_[i].GetName() == abilityInfo.GetName()) {
HILOG_DEBUG("the ability is already exist.");
return;
}
}
installedAbilities_.push_back(abilityInfo);
UpdateInstallAbilityListsState();
HILOG_DEBUG("push back installed ability successfully and installedAbilities_'s size is %{public}zu",
installedAbilities_.size());
}
void AccessibleAbilityManager::RemoveInstalledAbility(const std::string &bundleName)
{
HILOG_DEBUG("start.");
for (auto it = installedAbilities_.begin(); it != installedAbilities_.end();) {
if (it->GetPackageName() == bundleName) {
HILOG_DEBUG("Removed %{public}s from InstalledAbility: ", bundleName.c_str());
it = installedAbilities_.erase(it);
} else {
++it;
}
}
UpdateInstallAbilityListsState();
}
void AccessibleAbilityManager::UpdateInstallAbilityListsState()
{
std::lock_guard<ffrt::mutex> lock(enableAbilityListObserversMutex_);
HILOG_DEBUG("observer's size is %{public}zu", enableAbilityListsObservers_.size());
for (auto &observer : enableAbilityListsObservers_) {
if (observer) {
observer->OnAccessibilityInstallAbilityListsChanged();
}
}
}
void AccessibleAbilityManager::ClearInstalledAbility()
{
HILOG_DEBUG("start.");
installedAbilities_.clear();
}
const std::vector<AccessibilityAbilityInfo> &AccessibleAbilityManager::GetInstalledAbilities() const
{
HILOG_DEBUG("GetInstalledAbilities start.");
return installedAbilities_;
}
RetError AccessibleAbilityManager::UpdateInstalledAbility(const std::string &name, uint32_t capabilities)
{
for (auto iter = installedAbilities_.begin(); iter != installedAbilities_.end(); iter++) {
if (iter->GetId() == name) {
uint32_t resultCapabilities = iter->GetStaticCapabilityValues() & capabilities;
if (resultCapabilities == 0) {
HILOG_ERROR("the result of capabilities is wrong");
return RET_ERR_NOT_ENABLED;
}
iter->SetCapabilityValues(resultCapabilities);
return RET_OK;
}
}
return RET_ERR_NOT_INSTALLED;
}
void AccessibleAbilityManager::GetAbilitiesByState(
AbilityStateType state, std::vector<AccessibilityAbilityInfo> &abilities)
{
HILOG_DEBUG("get abilities by state %{public}d", state);
if (state == ABILITY_STATE_ENABLE) {
connectedA11yAbilities_.GetAbilitiesInfo(abilities);
} else if (state == ABILITY_STATE_DISABLE) {
GetDisableAbilities(abilities);
HILOG_DEBUG("the size of disable abilities is %{public}zu", abilities.size());
} else {
abilities = installedAbilities_;
}
}
void AccessibleAbilityManager::GetDisableAbilities(std::vector<AccessibilityAbilityInfo> &disabledAbilities)
{
HILOG_DEBUG("get disable abilities");
disabledAbilities = installedAbilities_;
connectedA11yAbilities_.GetDisableAbilities(disabledAbilities);
}
void AccessibleAbilityManager::AddEnableAbilityListsObserver(
const sptr<IAccessibilityEnableAbilityListsObserver> &observer)
{
HILOG_DEBUG();
std::lock_guard<ffrt::mutex> lock(enableAbilityListObserversMutex_);
if (std::any_of(enableAbilityListsObservers_.begin(), enableAbilityListsObservers_.end(),
[observer](const sptr<IAccessibilityEnableAbilityListsObserver> &listObserver) {
return listObserver == observer;
})) {
HILOG_ERROR("observer is already exist");
return;
}
enableAbilityListsObservers_.push_back(observer);
HILOG_DEBUG("observer's size is %{public}zu", enableAbilityListsObservers_.size());
}
void AccessibleAbilityManager::RemoveEnableAbilityListsObserver(const wptr<IRemoteObject>& observer)
{
HILOG_INFO();
std::lock_guard<ffrt::mutex> lock(enableAbilityListObserversMutex_);
for (auto itr = enableAbilityListsObservers_.begin(); itr != enableAbilityListsObservers_.end(); itr++) {
if ((*itr)->AsObject() == observer) {
HILOG_DEBUG("erase observer");
enableAbilityListsObservers_.erase(itr);
HILOG_DEBUG("observer's size is %{public}zu", enableAbilityListsObservers_.size());
return;
}
}
}
void AccessibleAbilityManager::UpdateEnableAbilityListsState()
{
std::lock_guard<ffrt::mutex> lock(enableAbilityListObserversMutex_);
HILOG_DEBUG("observer's size is %{public}zu", enableAbilityListsObservers_.size());
for (auto &observer : enableAbilityListsObservers_) {
if (observer) {
observer->OnAccessibilityEnableAbilityListsChanged();
}
}
}
void AccessibleAbilityManager::AddEnableAbilityCallbackObserver(
const sptr<IAccessibilityEnableAbilityCallbackObserver> &observer)
{
std::lock_guard<ffrt::mutex> lock(enableAbilityCallbackObserversMutex_);
if (std::any_of(enableAbilityCallbackObservers_.begin(), enableAbilityCallbackObservers_.end(),
[observer](const sptr<IAccessibilityEnableAbilityCallbackObserver> &listObserver) {
return listObserver == observer;
})) {
HILOG_ERROR("observer is already exist");
return;
}
enableAbilityCallbackObservers_.push_back(observer);
HILOG_DEBUG("observer's size is %{public}zu", enableAbilityCallbackObservers_.size());
}
void AccessibleAbilityManager::RemoveEnableAbilityCallbackObserver(const wptr<IRemoteObject>& observer)
{
std::lock_guard<ffrt::mutex> lock(enableAbilityCallbackObserversMutex_);
auto itr = enableAbilityCallbackObservers_.begin();
for (; itr != enableAbilityCallbackObservers_.end(); itr++) {
if ((*itr)->AsObject() == observer) {
HILOG_DEBUG("erase observer");
enableAbilityCallbackObservers_.erase(itr);
HILOG_DEBUG("observer's size is %{public}zu", enableAbilityCallbackObservers_.size());
return;
}
}
}
void AccessibleAbilityManager::CallEnableAbilityCallback(const std::string &uri)
{
std::lock_guard<ffrt::mutex> lock(enableAbilityCallbackObserversMutex_);
HILOG_DEBUG("observer's size is %{public}zu", enableAbilityCallbackObservers_.size());
for (auto &observer : enableAbilityCallbackObservers_) {
if (observer) {
observer->OnEnableAbilityRemoteDied(uri);
}
}
}
void AccessibleAbilityManager::NotifyExtensionServiceDeath(const std::string& uri)
{
HILOG_DEBUG("Notifying extension service death: uri=%{public}s", uri.c_str());
CallEnableAbilityCallback(uri);
}
bool AccessibleAbilityManager::RemoveAbility(const std::string &bundleName)
{
HILOG_DEBUG("bundleName(%{public}s)", bundleName.c_str());
if (installedAbilities_.empty()) {
HILOG_DEBUG("There is no installed abilities.");
return false;
}
RemoveInstalledAbility(bundleName);
bool result = false;
for (auto& enableAbility : enabledAbilities_) {
if (enableAbility.substr(0, enableAbility.find("/")) == bundleName) {
RemoveEnabledAbility(enableAbility);
RemoveConnectingAbility(enableAbility);
result = true;
}
}
RemoveConnectedAbilityByName(bundleName, result);
return result;
}
void AccessibleAbilityManager::AddAbility(const std::string &bundleName,
const std::vector<AccessibilityAbilityInfo>& abilityInfos,
std::function<bool(const std::string&)> autoStartChecker)
{
HILOG_DEBUG("bundleName(%{public}s)", bundleName.c_str());
for (auto &newAbility : abilityInfos) {
if (newAbility.GetPackageName() == bundleName) {
HILOG_DEBUG("The package%{public}s added", (bundleName + "/" + newAbility.GetName()).c_str());
AccessibilityAbilityInfo info = newAbility;
std::string abilityId = info.GetId();
if (autoStartChecker && autoStartChecker(abilityId)) {
HILOG_DEBUG("auto start packageName is %{public}s.", bundleName.c_str());
uint32_t capabilities = CAPABILITY_GESTURE | CAPABILITY_KEY_EVENT_OBSERVER | CAPABILITY_RETRIEVE |
CAPABILITY_TOUCH_GUIDE | CAPABILITY_ZOOM;
uint32_t resultCapabilities = info.GetStaticCapabilityValues() & capabilities;
info.SetCapabilityValues(resultCapabilities);
AddInstalledAbility(info);
std::string uri = Utils::GetUri(bundleName, info.GetName());
AddEnabledAbility(uri);
RemoveConnectingAbility(uri);
continue;
}
AddInstalledAbility(info);
}
}
}
void AccessibleAbilityManager::ChangeAbility(const std::string &bundleName,
std::function<bool(const std::string&)> autoStartChecker,
std::function<void(const std::string&, bool)> autoStartSetter)
{
HILOG_DEBUG("bundleName(%{public}s)", bundleName.c_str());
if (installedAbilities_.empty()) {
HILOG_DEBUG("There is no installed abilities.");
return;
}
std::vector<std::string> autoStartAbilities;
for (auto &ability : installedAbilities_) {
if (ability.GetPackageName() != bundleName) {
continue;
}
if (autoStartChecker && autoStartChecker(ability.GetId())) {
autoStartAbilities.push_back(ability.GetId());
}
}
RemoveInstalledAbility(bundleName);
for (auto &name : autoStartAbilities) {
auto iter = std::find_if(installedAbilities_.begin(), installedAbilities_.end(),
[&name](const AccessibilityAbilityInfo& info) {
return info.GetId() == name;
});
if (iter == installedAbilities_.end()) {
if (autoStartSetter) {
autoStartSetter(name, false);
}
}
}
}
void AccessibleAbilityManager::GetImportantEnabledAbilities(
std::map<std::string, uint32_t> &importantEnabledAbilities) const
{
HILOG_DEBUG("GetImportantEnabledAbilities start.");
if (installedAbilities_.empty()) {
HILOG_DEBUG("Current user has no installed Abilities.");
return;
}
if (enabledAbilities_.empty()) {
HILOG_DEBUG("Current user has no enabled abilities.");
return;
}
HILOG_DEBUG("installedAbilities_'s is %{public}zu.", installedAbilities_.size());
for (auto &installAbility : installedAbilities_) {
if (!installAbility.IsImportant()) {
HILOG_DEBUG("The ability is not important.");
continue;
}
std::string bundleName = installAbility.GetPackageName();
std::string abilityName = installAbility.GetName();
HILOG_DEBUG("installAbility's packageName is %{public}s and abilityName is %{public}s",
bundleName.c_str(), abilityName.c_str());
std::string uri = Utils::GetUri(bundleName, abilityName);
std::vector<std::string>::const_iterator iter = std::find(enabledAbilities_.begin(),
enabledAbilities_.end(), uri);
if (iter != enabledAbilities_.end()) {
uint32_t capabilityValues = installAbility.GetCapabilityValues();
importantEnabledAbilities.emplace(std::make_pair(uri, capabilityValues));
}
}
}
void AccessibleAbilityManager::UpdateImportantEnabledAbilities(
std::map<std::string, uint32_t> &importantEnabledAbilities)
{
HILOG_DEBUG();
if (importantEnabledAbilities.empty()) {
HILOG_DEBUG("There is no enabled abilities.");
return;
}
if (installedAbilities_.empty()) {
HILOG_DEBUG("Current user has no installedAbilities.");
return;
}
HILOG_DEBUG("installedAbilities is %{public}zu.", installedAbilities_.size());
for (auto &installAbility : installedAbilities_) {
std::string bundleName = installAbility.GetPackageName();
std::string abilityName = installAbility.GetName();
HILOG_DEBUG("installAbility's packageName is %{public}s and abilityName is %{public}s",
bundleName.c_str(), abilityName.c_str());
std::string uri = Utils::GetUri(bundleName, abilityName);
std::map<std::string, uint32_t>::iterator iter = importantEnabledAbilities.find(uri);
if (iter != importantEnabledAbilities.end()) {
AddEnabledAbility(uri);
installAbility.SetCapabilityValues(iter->second);
}
}
}
void AccessibleAbilityManager::UpdateAutoStartEnabledAbilities(std::function<bool(const std::string&)> autoStartChecker)
{
HILOG_DEBUG();
if (installedAbilities_.empty()) {
HILOG_DEBUG("Current user has no installedAbilities.");
return;
}
HILOG_DEBUG("installedAbilities is %{public}zu.", installedAbilities_.size());
for (auto &installAbility : installedAbilities_) {
std::string bundleName = installAbility.GetPackageName();
std::string abilityName = installAbility.GetName();
std::string abilityId = bundleName + "/" + abilityName;
if (autoStartChecker && autoStartChecker(abilityId)) {
HILOG_DEBUG("auto start packageName is %{public}s.", bundleName.c_str());
uint32_t capabilities = CAPABILITY_GESTURE | CAPABILITY_KEY_EVENT_OBSERVER | CAPABILITY_RETRIEVE |
CAPABILITY_TOUCH_GUIDE | CAPABILITY_ZOOM;
uint32_t resultCapabilities = installAbility.GetStaticCapabilityValues() & capabilities;
installAbility.SetCapabilityValues(resultCapabilities);
std::string uri = Utils::GetUri(bundleName, abilityName);
AddEnabledAbility(uri);
}
}
}
bool AccessibleAbilityManager::IsExistCapability(Capability capability)
{
return connectedA11yAbilities_.IsExistCapability(capability);
}
int32_t AccessibleAbilityManager::GetSizeByUri(const std::string& uri)
{
return connectedA11yAbilities_.GetSizeByUri(uri);
}
void AccessibleAbilityManager::UpdateAbilities(
const std::string& callerBundleName,
int32_t accountId,
uint32_t& connectCounter,
std::function<sptr<AccessibleAbilityConnection>(
int32_t, int32_t, AccessibilityAbilityInfo&)> connectionCreator)
{
HILOG_DEBUG("UpdateAbilities start.");
for (auto& installAbility : installedAbilities_) {
std::string uri = Utils::GetUri(installAbility.GetPackageName(), installAbility.GetName());
HILOG_DEBUG("installAbility's packageName is %{public}s and abilityName is %{public}s",
installAbility.GetPackageName().c_str(), installAbility.GetName().c_str());
if (connectingA11yAbilities_.GetSizeByUri(
Utils::GetUri(installAbility.GetPackageName(), installAbility.GetName()))) {
HILOG_DEBUG("The ability(bundleName[%{public}s] abilityName[%{public}s]) is connecting.",
installAbility.GetPackageName().c_str(),
installAbility.GetName().c_str());
continue;
}
auto connection = GetConnectedAbilityByName(uri);
bool isEnabled = IsAbilityEnabled(uri);
if (isEnabled && !connection) {
if (!connectionCreator) {
HILOG_ERROR("connectionCreator is null");
continue;
}
connection = connectionCreator(accountId, connectCounter++, installAbility);
if (connection && ConnectAbility(connection, installAbility, callerBundleName)) {
AddConnectingAbility(uri, connection);
}
} else if (!isEnabled && connection) {
HILOG_DEBUG("not in enabledAbilites list.");
DisconnectAbility(connection, uri);
}
}
}
bool AccessibleAbilityManager::IsAbilityEnabled(const std::string& uri)
{
const auto& enabledAbilities = GetEnabledAbilities();
return std::find(enabledAbilities.begin(), enabledAbilities.end(), uri) != enabledAbilities.end();
}
bool AccessibleAbilityManager::ConnectAbility(
sptr<AccessibleAbilityConnection>& connection,
const AccessibilityAbilityInfo& ability,
const std::string& callerBundleName)
{
AppExecFwk::ElementName element("", ability.GetPackageName(), ability.GetName());
if (!connection->Connect(element)) {
HILOG_ERROR("Connect failed for %{public}s", ability.GetId().c_str());
return false;
}
if (!callerBundleName.empty()) {
connection->SetConnectionKey(callerBundleName);
}
return true;
}
void AccessibleAbilityManager::DisconnectAbility(
sptr<AccessibleAbilityConnection>& connection,
const std::string& uri)
{
AddWaitDisconnectAbility(connection);
RemoveConnectedAbility(connection->GetElementName());
connection->Disconnect();
}
RetError AccessibleAbilityManager::GetReadableRules(std::string &readableRules)
{
HILOG_INFO();
for (auto &installAbility : installedAbilities_) {
if (installAbility.GetPackageName() == SCREEN_READER_BUNDLE_NAME) {
readableRules = installAbility.GetReadableRules();
return RET_OK;
}
}
return RET_ERR_NOT_INSTALLED;
}
void AccessibleAbilityManager::AccessibilityAbility::AddAccessibilityAbility(const std::string& uri,
const sptr<AccessibleAbilityConnection>& connection)
{
HILOG_INFO("uri is %{private}s", uri.c_str());
std::lock_guard<ffrt::mutex> lock(mutex_);
if (!connectionMap_.count(uri)) {
connectionMap_[uri] = connection;
HILOG_DEBUG("connectionMap_ size %{public}zu", connectionMap_.size());
return;
}
HILOG_DEBUG("uri %{private}s, connectionMap_ %{public}zu", uri.c_str(), connectionMap_.size());
}
sptr<AccessibleAbilityConnection> AccessibleAbilityManager::AccessibilityAbility::GetAccessibilityAbilityByName(
const std::string& elementName)
{
HILOG_DEBUG("elementName is %{public}s", elementName.c_str());
std::lock_guard<ffrt::mutex> lock(mutex_);
for (auto& connection : connectionMap_) {
std::string::size_type index = connection.first.find(elementName);
if (index == std::string::npos) {
continue;
} else {
HILOG_DEBUG("uri %{private}s ", connection.first.c_str());
return connection.second;
}
}
return nullptr;
}
sptr<AccessibleAbilityConnection> AccessibleAbilityManager::AccessibilityAbility::GetAccessibilityAbilityByUri(
const std::string& uri)
{
HILOG_DEBUG("uri is %{private}s", uri.c_str());
std::lock_guard<ffrt::mutex> lock(mutex_);
auto iter = connectionMap_.find(uri);
if (iter != connectionMap_.end()) {
return iter->second;
}
return nullptr;
}
void AccessibleAbilityManager::AccessibilityAbility::GetAccessibilityAbilities(
std::vector<sptr<AccessibleAbilityConnection>>& connectionList)
{
std::lock_guard<ffrt::mutex> lock(mutex_);
for (auto& connection : connectionMap_) {
connectionList.push_back(connection.second);
}
}
void AccessibleAbilityManager::AccessibilityAbility::GetAbilitiesInfo(std::vector<AccessibilityAbilityInfo>& abilities)
{
std::lock_guard<ffrt::mutex> lock(mutex_);
for (auto& connection : connectionMap_) {
if (connection.second) {
abilities.push_back(connection.second->GetAbilityInfo());
}
}
HILOG_DEBUG("connectionMap_ %{public}zu and enabledAbilities %{public}zu",
connectionMap_.size(), abilities.size());
}
bool AccessibleAbilityManager::AccessibilityAbility::IsExistCapability(Capability capability)
{
HILOG_DEBUG("capability %{public}d", capability);
std::lock_guard<ffrt::mutex> lock(mutex_);
for (auto iter = connectionMap_.begin(); iter != connectionMap_.end(); iter++) {
if (iter->second->GetAbilityInfo().GetCapabilityValues() & capability) {
return true;
}
}
return false;
}
void AccessibleAbilityManager::AccessibilityAbility::GetAccessibilityAbilitiesMap(
std::map<std::string, sptr<AccessibleAbilityConnection>>& connectionMap)
{
std::lock_guard<ffrt::mutex> lock(mutex_);
connectionMap = connectionMap_;
}
void AccessibleAbilityManager::AccessibilityAbility::GetDisableAbilities(
std::vector<AccessibilityAbilityInfo> &disabledAbilities)
{
std::lock_guard<ffrt::mutex> lock(mutex_);
for (auto& connection : connectionMap_) {
for (auto iter = disabledAbilities.begin(); iter != disabledAbilities.end();) {
if (connection.second && (iter->GetId() == connection.second->GetAbilityInfo().GetId())) {
iter = disabledAbilities.erase(iter);
} else {
iter++;
}
}
}
}
int32_t AccessibleAbilityManager::AccessibilityAbility::GetSizeByUri(const std::string& uri)
{
std::lock_guard<ffrt::mutex> lock(mutex_);
return connectionMap_.count(uri);
}
void AccessibleAbilityManager::AccessibilityAbility::RemoveAccessibilityAbilityByName(const std::string& bundleName,
bool& result)
{
std::lock_guard<ffrt::mutex> lock(mutex_);
for (auto& connection : connectionMap_) {
std::size_t firstPos = connection.first.find_first_of('/') + 1;
std::size_t endPos = connection.first.find_last_of('/');
if (endPos <= firstPos) {
HILOG_ERROR("it's a wrong ability and the uri %{public}s ", connection.first.c_str());
continue;
}
std::string connectedBundleName = connection.first.substr(firstPos, endPos - firstPos);
if (connectedBundleName == bundleName) {
HILOG_DEBUG("remove connected ability, bundle name %{public}s", connectedBundleName.c_str());
std::string uri = Utils::GetUri(connection.second->GetElementName());
auto it = connectionMap_.find(uri);
if (it != connectionMap_.end()) {
connectionMap_.erase(it);
}
result = true;
}
}
}
void AccessibleAbilityManager::AccessibilityAbility::RemoveAccessibilityAbilityByUri(const std::string& uri)
{
HILOG_INFO("uri is %{private}s", uri.c_str());
std::lock_guard<ffrt::mutex> lock(mutex_);
auto it = connectionMap_.find(uri);
if (it != connectionMap_.end()) {
connectionMap_.erase(it);
}
HILOG_DEBUG("connectionMap_ %{public}zu", connectionMap_.size());
}
void AccessibleAbilityManager::AccessibilityAbility::Clear()
{
std::lock_guard<ffrt::mutex> lock(mutex_);
return connectionMap_.clear();
}
size_t AccessibleAbilityManager::AccessibilityAbility::GetSize()
{
std::lock_guard<ffrt::mutex> lock(mutex_);
return connectionMap_.size();
}
}
}