/*
* Copyright (c) Huawei Technologies Co., Ltd. 2024-2025. All rights reserved.
* 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.
*/
import bundle from '@ohos.bundle.bundleManager';
import resourceManager from '@ohos.resourceManager';
import accessibility from '@ohos.accessibility';
import { LogUtil } from '@ohos/settings.common/src/main/ets/utils/LogUtil';
import { ServiceBaseEntry } from '@ohos/settings.common/src/main/ets/core/model/menu/SettingsMenu';
import { BaseEntryMenu } from '@ohos/settings.common/src/main/ets/core/model/menu/BaseMenu';
import { AbilityContextManager } from '@ohos/settings.common/src/main/ets/ability/AbilityContextManager';
import { MemoryMgrUtils } from '@ohos/settings.common/src/main/ets/utils/MemoryMgrUtils';
import { ResourceManagerUtil } from '@ohos/settings.common/src/main/ets/utils/ResourceManagerUtil';
/* instrument ignore file */
const TAG: string = 'ServiceModel: ';
const DEFAULT_ID: number = 0;
/**
* 扩展服务数据类
*
* @since 2023-06-26
*/
export class ServiceEntry implements ServiceBaseEntry {
public appInfo: bundle.ApplicationInfo;
public name: string;
public icon: ResourceStr;
public locale: string = '';
public description: string;
public serviceName: string;
public bundleName: string;
public serviceState: boolean;
public label: string;
public iconId: number = DEFAULT_ID;
public moduleInfo: Array<bundle.HapModuleInfo>;
public pageContext: Context = AbilityContextManager.getContext();
constructor(serviceInfo: bundle.ExtensionAbilityInfo | accessibility.AccessibilityAbilityInfo, state: boolean,
bundleInfo: bundle.BundleInfo) {
this.serviceName = serviceInfo.name;
this.bundleName = serviceInfo.bundleName;
this.description = '';
this.label = '';
this.serviceState = state;
this.appInfo = bundleInfo.appInfo;
this.iconId = bundleInfo.appInfo.iconId;
this.icon = '';
this.moduleInfo = bundleInfo.hapModulesInfo;
this.name = serviceInfo.bundleName + '/' + serviceInfo.name;
}
isLocaleMatch(locale: string): boolean {
return this.locale === locale;
}
private isResourceIdValid(id: number): boolean {
return !Number.isNaN(id) && id > DEFAULT_ID;
}
/**
* 异步加载图标
* @returns icon是否重新加载
*/
async loadIcon(): Promise<boolean> {
if (this.icon) {
LogUtil.info(`${TAG} loadIcon return`);
return false;
}
if (!this.isResourceIdValid(this.iconId)) {
LogUtil.warn(`${TAG} iconId invalid: ${this.iconId}`);
this.icon = this.getDefaultIcon();
return true;
}
let resourceManager = ResourceManagerUtil.getResManagerWithContext(this.bundleName, this.pageContext);
if (!resourceManager) {
LogUtil.warn(`${TAG} resourceManager invalid`);
this.icon = this.getDefaultIcon();
return true;
}
this.icon = await resourceManager.getMediaBase64(this.iconId);
if (!this.icon) {
LogUtil.warn(`${TAG} get icon invalid`);
this.icon = this.getDefaultIcon();
}
MemoryMgrUtils.removeNapiWrap(resourceManager, false);
return true;
}
private getDefaultIcon(): ResourceStr {
return $r('sys.media.ohos_app_icon');
}
/**
* 异步加载服务说明
* @returns description是否重新加载
*/
async loadDescription(): Promise<boolean> {
if (this.description) {
LogUtil.info(`${TAG} loadDescription return`);
return false;
}
if (this.moduleInfo) {
for (let hapInfo of this.moduleInfo) {
for (let ability of hapInfo.extensionAbilitiesInfo) {
if (ability.name === this.serviceName) {
let resourceManager = ResourceManagerUtil.getResManagerWithContext(this.bundleName, this.pageContext);
if (!resourceManager) {
LogUtil.warn(`${TAG} resourceManager invalid`);
return true;
}
if (!this.isResourceIdValid(ability.descriptionId)) {
LogUtil.info(`${TAG} descriptionId invalid: ${ability.descriptionId}`);
return true;
}
this.description = await resourceManager.getString(ability.descriptionId);
if (!this.description) {
LogUtil.warn(`${TAG} get description invalid`);
}
LogUtil.info(`${TAG} loadDescription end`);
MemoryMgrUtils.removeNapiWrap(resourceManager, false);
return true;
}
}
}
}
LogUtil.info(`${TAG} loadDescription end`);
return true;
}
/**
* 异步加载服务名称,使用label作为服务名称
* @returns label是否重新加载
*/
async loadLabel(): Promise<boolean> {
if (this.label) {
LogUtil.info(`${TAG} loadLabel return`);
return false;
}
this.label = await this.getLabelInfo();
if (!this.label) {
LogUtil.warn(`${TAG} get label invalid`);
}
LogUtil.info(`${TAG} loadLabel end`);
return true;
}
async getLabelInfo(): Promise<string> {
if (!this.moduleInfo) {
LogUtil.info(`${TAG} moduleInfo invalid`);
return '';
}
for (let hapInfo of this.moduleInfo) {
for (let ability of hapInfo.extensionAbilitiesInfo) {
if (ability.name != this.serviceName) {
continue;
}
let resourceManager = ResourceManagerUtil.getResManagerWithContext(ability.bundleName, this.pageContext);
if (!resourceManager) {
LogUtil.info(`${TAG} resourceManager invalid`);
return '';
}
if (!this.isResourceIdValid(ability.labelId)) {
LogUtil.info(`${TAG} descriptionId invalid: ${ability.labelId}`);
return '';
}
let label: string = await resourceManager.getString(ability.labelId);
if (!label) {
LogUtil.warn(`${TAG} get label invalid`);
return '';
}
MemoryMgrUtils.removeNapiWrap(resourceManager, false);
return label;
}
}
return '';
}
}
/**
* 扩展服务菜单数据类
*
* @since 2022-05-26
*/
export class ServiceMenu extends BaseEntryMenu {
public serviceEntry: ServiceEntry | null = null;
constructor(serviceEntry: ServiceEntry) {
super(serviceEntry);
this.updateEntry(serviceEntry);
}
updateEntry(serviceEntry: ServiceEntry): void {
this.serviceEntry = serviceEntry;
this.key = serviceEntry.name;
this.title = serviceEntry.label;
this.icon = serviceEntry.icon;
this.timestamp = new Date().getTime();
}
}
export class RecentServiceMenu extends ServiceMenu {
updateEntry(serviceEntry: ServiceEntry): void {
this.serviceEntry = serviceEntry;
this.title = serviceEntry.label;
this.icon = serviceEntry.icon;
this.timestamp = new Date().getTime();
}
}