“2ceb4ae941bd330d5e0cf6855847c014d49b42c3”上不存在“...transpiler/git@gitcode.net:s920243400/PaddleDetection.git”
提交 a04eb4cf 编写于 作者: G Gloria

Update docs against...

Update docs against 10892+18228+18418+18683+18264+18342+18228+18487+18336+18328+18057+18095+18330+18338+18333+18221+18344+16367+18093

Signed-off-by: wusongqing<wusongqing@huawei.com>
上级 827ee354
...@@ -20,7 +20,7 @@ ...@@ -20,7 +20,7 @@
- [AccessibilityExtensionAbility](accessibilityextensionability.md) - [AccessibilityExtensionAbility](accessibilityextensionability.md)
- [EnterpriseAdminExtensionAbility](enterprise-extensionAbility.md) - [EnterpriseAdminExtensionAbility](enterprise-extensionAbility.md)
- [InputMethodExtensionAbility](inputmethodextentionability.md) - [InputMethodExtensionAbility](inputmethodextentionability.md)
- [WindowExtensionAbility](windowextensionability.md) - [WindowExtensionAbility (for System Applications Only)](windowextensionability.md)
- Service Widget Development in Stage Model - Service Widget Development in Stage Model
- [Service Widget Overview](service-widget-overview.md) - [Service Widget Overview](service-widget-overview.md)
- Developing an ArkTS Widget - Developing an ArkTS Widget
...@@ -52,7 +52,7 @@ ...@@ -52,7 +52,7 @@
- [Want Overview](want-overview.md) - [Want Overview](want-overview.md)
- [Matching Rules of Explicit Want and Implicit Want](explicit-implicit-want-mappings.md) - [Matching Rules of Explicit Want and Implicit Want](explicit-implicit-want-mappings.md)
- [Common action and entities Values](actions-entities.md) - [Common action and entities Values](actions-entities.md)
- [Using Explicit Want to Start an Ability](ability-startup-with-explicit-want.md) - [Using Explicit Want to Start an Application Component](ability-startup-with-explicit-want.md)
- [Using Implicit Want to Open a Website](ability-startup-with-implicit-want.md) - [Using Implicit Want to Open a Website](ability-startup-with-implicit-want.md)
- [Using Want to Share Data Between Applications](data-share-via-want.md) - [Using Want to Share Data Between Applications](data-share-via-want.md)
- [Component Startup Rules](component-startup-rules.md) - [Component Startup Rules](component-startup-rules.md)
...@@ -78,10 +78,10 @@ ...@@ -78,10 +78,10 @@
- [Using Worker for Inter-Thread Communication](itc-with-worker.md) - [Using Worker for Inter-Thread Communication](itc-with-worker.md)
- Mission Management - Mission Management
- [Mission Management Scenarios](mission-management-overview.md) - [Mission Management Scenarios](mission-management-overview.md)
- [Mission Management and Launch Type](mission-management-launch-type.md) - [Mission and Launch Type](mission-management-launch-type.md)
- [Page Stack and MissionList](page-mission-stack.md) - [Page Stack and MissionList](page-mission-stack.md)
- [Setting the Icon and Name of a Mission Snapshot](mission-set-icon-name-for-task-snapshot.md) - [Setting the Icon and Name of a Mission Snapshot](mission-set-icon-name-for-task-snapshot.md)
- [Application Configuration File (Stage Model)](config-file-stage.md) - [Application Configuration File](config-file-stage.md)
- FA Model Development - FA Model Development
- [FA Model Development Overview](fa-model-development-overview.md) - [FA Model Development Overview](fa-model-development-overview.md)
- FA Mode Application Components - FA Mode Application Components
......
# Using Explicit Want to Start an Ability # Using Explicit Want to Start an Application Component
When a user touches a button in an application, the application often needs to start a UIAbility component to complete a specific task. If the **abilityName** and **bundleName** parameters are specified when starting a UIAbility, then the explicit Want is used. Using Explicit Want When a user touches a button in an application, the application often needs to start a UIAbility component to complete a specific task. If the **abilityName** and **bundleName** parameters are specified when starting a UIAbility, then the explicit Want is used.
## Using Explicit Want
The user touches a button in the application to start the UIAbility component to complete a specific task. To start the UIAbility component in explicit Want mode, the **abilityName** and **bundleName** parameters must be specified. For details, see [Starting UIAbility in the Same Application](uiability-intra-device-interaction.md#starting-uiability-in-the-same-application). The user touches a button in the application to start the UIAbility component to complete a specific task. To start the UIAbility component in explicit Want mode, the **abilityName** and **bundleName** parameters must be specified. For details, see [Starting UIAbility in the Same Application](uiability-intra-device-interaction.md#starting-uiability-in-the-same-application).
...@@ -5,21 +5,21 @@ This section uses the operation of using a browser to open a website as an examp ...@@ -5,21 +5,21 @@ This section uses the operation of using a browser to open a website as an examp
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
// ... ...
"skills": [ "skills": [
{ {
"entities": [ "entities": [
"entity.system.home", "entity.system.home",
"entity.system.browsable" "entity.system.browsable"
// ... ...
], ],
"actions": [ "actions": [
"action.system.home", "action.system.home",
"ohos.want.action.viewData" "ohos.want.action.viewData"
// ... ...
], ],
"uris": [ "uris": [
{ {
...@@ -31,9 +31,9 @@ This section uses the operation of using a browser to open a website as an examp ...@@ -31,9 +31,9 @@ This section uses the operation of using a browser to open a website as an examp
}, },
{ {
"scheme": "http", "scheme": "http",
// ... ...
} }
// ... ...
] ]
} }
] ]
...@@ -59,20 +59,19 @@ function implicitStartAbility() { ...@@ -59,20 +59,19 @@ function implicitStartAbility() {
'uri': 'https://www.test.com:8080/query/student' 'uri': 'https://www.test.com:8080/query/student'
} }
context.startAbility(wantInfo).then(() => { context.startAbility(wantInfo).then(() => {
// ... ...
}).catch((err) => { }).catch((err) => {
// ... ...
}) })
} }
``` ```
The matching process is as follows: The matching process is as follows:
1. If **action** in the passed **want** parameter is specified and is included in **actions** under **skills** of the ability to match, the matching is successful. 1. If **action** in the passed **want** parameter is specified and is included in **actions** under **skills** of the application component to match, the matching is successful.
2. If **entities** in the passed **want** parameter is specified and is included in **entities** under **skills** of the ability to match, the matching is successful. 2. If **entities** in the passed **want** parameter is specified and is included in **entities** under **skills** of the application component to match, the matching is successful.
3. If **uri** in the passed **want** parameter is included in **uris** under **skills** of the ability to match, which is concatenated into https://www.test.com:8080/query* (where * is a wildcard), the matching is successful. 3. If **uri** in the passed **want** parameter is included in **uris** under **skills** of the application component to match, which is concatenated into https://www.test.com:8080/query* (where * is a wildcard), the matching is successful.
4. If **type** in the passed **want** parameter is specified and is included in **type** under **skills** of the ability to match, the matching is successful.
If there are multiple matching applications, the system displays a dialog box for you to select one of them. The following figure shows an example. If there are multiple matching applications, the system displays a dialog box for you to select one of them. The following figure shows an example.
![stage-want1](figures/stage-want1.png) ![](figures/ability-startup-with-implicit-want1.png)
\ No newline at end of file
...@@ -24,20 +24,20 @@ AbilityStage is not automatically generated in the default project of DevEco Stu ...@@ -24,20 +24,20 @@ AbilityStage is not automatically generated in the default project of DevEco Stu
// When the HAP of the application is loaded for the first time, initialize the module. // When the HAP of the application is loaded for the first time, initialize the module.
} }
onAcceptWant(want) { onAcceptWant(want) {
// Triggered only for the ability with the specified launch type. // Triggered only for the UIAbility with the specified launch type.
return "MyAbilityStage"; return "MyAbilityStage";
} }
} }
``` ```
4. Set **srcEntry** in the [module.json5 file](../quick-start/module-configuration-file.md) to the code path of the module. 4. In the [module.json5 file](../quick-start/module-configuration-file.md), set **srcEntry** to specify the code path of the module as the entry for loading the HAP.
```json ```json
{ {
"module": { "module": {
"name": "entry", "name": "entry",
"type": "entry", "type": "entry",
"srcEntry": "./ets/myabilitystage/MyAbilityStage.ts", "srcEntry": "./ets/myabilitystage/MyAbilityStage.ts",
// ... ...
} }
} }
``` ```
......
# Common action and entities Values # Common action and entities Values
The [action](../reference/apis/js-apis-ability-wantConstant.md#wantconstantaction) field specifies the common operation (such as viewing, sharing, and application details) to be performed by the caller. In implicit Want, you can define this field and use it together with **uri** or **parameters** to specify the operation to be performed on the data, for example, viewing URI data. For example, if the URI is a website and the action is **ohos.want.action.viewData**, the ability that supports website viewing is matched. Declaring the **action** field in Want indicates that the invoked application should support the declared operation. The **actions** field under **skills** in the configuration file indicates the operations supported by the application. The **action** field specifies the common operation (such as viewing, sharing, and application details) to be performed by the caller. In implicit [Want](../reference/apis/js-apis-app-ability-want.md), you can define this field and use it together with **uri** or **parameters** to specify the operation to be performed on the data, for example, viewing URI data. For example, if the URI is a website and the action is **ohos.want.action.viewData**, the application component that supports website viewing is matched. Declaring the **action** field in [Want](../reference/apis/js-apis-app-ability-want.md) indicates that the invoked application is expected to support the declared operation. The **actions** field under **skills** in the configuration file indicates the operations supported by the application.
The following **action** values are available:
**Common action Values**
- **ACTION_HOME**: action of starting the application entry component. It must be used together with **ENTITY_HOME**. The application icon on the home screen is an explicit entry component. Users can touch the icon to start the entry component. Multiple entry components can be configured for an application. - **ACTION_HOME**: action of starting the application entry component. It must be used together with **ENTITY_HOME**. The application icon on the home screen is an explicit entry component. Users can touch the icon to start the entry component. Multiple entry components can be configured for an application.
...@@ -14,14 +13,13 @@ The [action](../reference/apis/js-apis-ability-wantConstant.md#wantconstantactio ...@@ -14,14 +13,13 @@ The [action](../reference/apis/js-apis-ability-wantConstant.md#wantconstantactio
- **ACTION_VIEW_MULTIPLE_DATA**: action of launching the UI for sending multiple data records. - **ACTION_VIEW_MULTIPLE_DATA**: action of launching the UI for sending multiple data records.
The [entities](../reference/apis/js-apis-ability-wantConstant.md#wantconstantentity) field specifies the additional category information (such as browser and video player) of the target ability. It is a supplement to **action** in implicit Want. You can define this field to filter application categories, for example, browser. Declaring the **entities** field in Want indicates that the invoked application should belong to the declared category. The **entities** field under **skills** in the configuration file indicates the categories supported by the application. The **entities** field specify the category information (such as browser and video player) of the target application component. It is a supplement to **action** in implicit Want. You can define this field to filter application categories, for example, browser. Declaring the **entities** field in Want indicates that the invoked application should belong to the declared category. The **entities** field under **skills** in the configuration file indicates the categories supported by the application.
**Common entities Values** The following **entities** values are available:
- **ENTITY_DEFAULT**: default category, which is meaningless. - **ENTITY_DEFAULT**: default category, which is meaningless.
- **ENTITY_HOME**: abilities with an icon displayed on the home screen. - **ENTITY_HOME**: application components with an icon displayed on the home screen.
- **ENTITY_BROWSABLE**: browser type. - **ENTITY_BROWSABLE**: browser type.
...@@ -22,7 +22,7 @@ OpenHarmony has reconstructed the [deviceConfig](../quick-start/deviceconfig-str ...@@ -22,7 +22,7 @@ OpenHarmony has reconstructed the [deviceConfig](../quick-start/deviceconfig-str
| deviceConfig in the FA Model| Description| Stage Model| Difference| | deviceConfig in the FA Model| Description| Stage Model| Difference|
| -------- | -------- | -------- | -------- | | -------- | -------- | -------- | -------- |
| deviceConfig| Device information.| / | This tag is no longer available in the stage model. In the stage model, device information is configured under the **app** tag.| | deviceConfig| Device information.| / | This tag is no longer available in the stage model. In the stage model, device information is configured under the **app** tag.|
| process | Name of the process running the application or ability. If the **process** attribute is configured in the **deviceConfig** tag, all abilities of the application run in this process. You can set the **process** attribute for a specific ability in the **abilities** attribute, so that the ability can run in the particular process.| / | The stage model does not support the configuration of process names.| | process | Name of the process running the application or UIAbility. If the **process** attribute is configured in the **deviceConfig** tag, all UIAbilities of the application run in this process. You can set the **process** attribute for a specific UIAbility in the **abilities** attribute, so that the UIAbility can run in the particular process.| / | The stage model does not support the configuration of process names.|
| keepAlive | Whether the application is always running. This attribute applies only to system applications and does not take effect for third-party applications.| / | The stage model does not support changing of the model control mode for system applications.| | keepAlive | Whether the application is always running. This attribute applies only to system applications and does not take effect for third-party applications.| / | The stage model does not support changing of the model control mode for system applications.|
| supportBackup | Whether the application supports data backup and restore.| / | This configuration is not supported in the stage model.| | supportBackup | Whether the application supports data backup and restore.| / | This configuration is not supported in the stage model.|
| compressNativeLibs | Whether the **libs** libraries are packaged in the HAP file after being compressed.| / | This configuration is not supported in the stage model.| | compressNativeLibs | Whether the **libs** libraries are packaged in the HAP file after being compressed.| / | This configuration is not supported in the stage model.|
......
...@@ -22,7 +22,7 @@ When developing an application, you may need to configure certain tags to identi ...@@ -22,7 +22,7 @@ When developing an application, you may need to configure certain tags to identi
"actions": ["action.system.home"] "actions": ["action.system.home"]
} }
] ]
// ... ...
} }
``` ```
......
# Application- or Component-Level Configuration (Stage Model) # Application- or Component-Level Configuration (Stage Model)
When developing an application, you may need to configure certain tags to identify the application, such as the bundle name and application icon. This topic describes key tags that need to be configured during application development.
When developing an application, you may need to configure certain tags to identify the application, such as the bundle name and application icon. This topic describes key tags that need to be configured during application development. Icons and labels are usually configured together. There is the application icon, application label, entry icon, and entry label, which correspond to the **icon** and **label** fields in the [app.json5 file](../quick-start/app-configuration-file.md) and [module.json5 file](../quick-start/module-configuration-file.md). The application icon and label are used in **Settings**. For example, they are displayed in the application list in **Settings**. The entry icon is displayed on the device's home screen after the application is installed. The entry icon maps to a [UIAbility](uiability-overview.md) component. Therefore, an application can have multiple entry icons and labels. When you touch one of them, the corresponding UIAbility page is displayed. Icons and labels are usually configured together. There is the application icon, application label, entry icon, and entry label, which correspond to the **icon** and **label** fields in the [app.json5 file](../quick-start/app-configuration-file.md) and [module.json5 file](../quick-start/module-configuration-file.md).
The application icon and label are used in **Settings**. For example, they are displayed in the application list in **Settings**. The entry icon is displayed on the device's home screen after the application is installed. The entry icon maps to a [UIAbility](uiability-overview.md) component. Therefore, an application can have multiple entry icons and entry labels. When you touch one of them, the corresponding UIAbility page is displayed.
**Figure 1** Icons and labels **Figure 1** Icons and labels
![application-component-configuration-stage](figures/application-component-configuration-stage.png) ![application-component-configuration-stage](figures/application-component-configuration-stage.png)
...@@ -22,13 +24,13 @@ When developing an application, you may need to configure certain tags to identi ...@@ -22,13 +24,13 @@ When developing an application, you may need to configure certain tags to identi
The application label is specified by the **label** field in the [app.json5 file](../quick-start/app-configuration-file.md) in the **AppScope** module of the project. The **label** field specifies the application name displayed to users. It must be set to the index of a string resource. The application label is specified by the **label** field in the [app.json5 file](../quick-start/app-configuration-file.md) in the **AppScope** module of the project. The **label** field specifies the application name displayed to users. It must be set to the index of a string resource.
```json ```json
{ {
"app": { "app": {
"icon": "$media:app_icon", "icon": "$media:app_icon",
"label": "$string:app_name" "label": "$string:app_name"
// ... ...
}
} }
}
``` ```
- **Configuring the entry icon and label** - **Configuring the entry icon and label**
...@@ -40,7 +42,7 @@ When developing an application, you may need to configure certain tags to identi ...@@ -40,7 +42,7 @@ When developing an application, you may need to configure certain tags to identi
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
// The information starting with $ is the resource value. // The information starting with $ is the resource value.
...@@ -61,6 +63,35 @@ When developing an application, you may need to configure certain tags to identi ...@@ -61,6 +63,35 @@ When developing an application, you may need to configure certain tags to identi
} }
} }
``` ```
OpenHarmony strictly controls applications without icons to prevent malicious applications from deliberately configuring no icon to block uninstall attempts.
To hide an application icon from the home screen, you must configure the **AllowAppDesktopIconHide** privilege. For details, see [Application Privilege Configuration Guide](../../device-dev/subsystems/subsys-app-privilege-config-guide.md). The rules for displaying the entry icon and entry label are as follows:
1. The HAP file contains UIAbility configuration.
* An entry icon is set in the **abilities** field of the **module.json5** file.
* The application does not have the privilege to hide its icon from the home screen.
* The system uses the icon configured for the UIAbility as the entry icon and displays it on the home screen. Touching this icon will direct the user to the home page of the UIAbility.
* The system uses the label configured for the UIAbility as the entry label and displays it on the home screen. If no label is configured, the system uses the label specified in the **app.json5** file as the entry label and displays it on the home screen.
* The application has the privilege to hide its icon from the home screen.
* The application information is not returned when the home screen queries the information, and the entry icon and label of the application are not displayed on the home screen.
* No entry icon is set in the **abilities** field of the **module.json5** file.
* The application does not have the privilege to hide its icon from the home screen.
* The system uses the icon specified in the **app.json5** file as the entry icon and displays it on the home screen. Touching this icon will direct the user to the application details page, as shown below.
* The system uses the label specified in the **app.json5** file as the entry label and displays it on the home screen.
* The application has the privilege to hide its icon from the home screen.
* The application information is not returned when the home screen queries the information, and the entry icon and label of the application are not displayed on the home screen.
2. The HAP file does not contain UIAbility configuration.
* The application does not have the privilege to hide its icon from the home screen.
* The system uses the icon specified in the **app.json5** file as the entry icon and displays it on the home screen. Touching this icon will direct the user to the application details page, as shown below.
* The system uses the label specified in the **app.json5** file as the entry label and displays it on the home screen.
* The application has the privilege to hide its icon from the home screen.
* The application information is not returned when the home screen queries the information, and the entry icon and label of the application are not displayed on the home screen.
**Figure 2** Application details page
![Application details page](figures/application_details.jpg)
- **Configuring application version declaration** - **Configuring application version declaration**
To declare the application version, configure the **versionCode** and **versionName** fields in the [app.json5 file](../quick-start/app-configuration-file.md) in the **AppScope** directory of the project. **versionCode** specifies the version number of the application. The value is a 32-bit non-negative integer. It is used only to determine whether a version is later than another version. A larger value indicates a later version. **versionName** provides the text description of the version number. To declare the application version, configure the **versionCode** and **versionName** fields in the [app.json5 file](../quick-start/app-configuration-file.md) in the **AppScope** directory of the project. **versionCode** specifies the version number of the application. The value is a 32-bit non-negative integer. It is used only to determine whether a version is later than another version. A larger value indicates a later version. **versionName** provides the text description of the version number.
......
# Context (Stage Model) # Context (Stage Model)
## Overview ## Overview
[Context](../reference/apis/js-apis-inner-application-context.md) is the context of an object in an application. It provides basic information about the application, for example, **resourceManager**, **applicationInfo**, **dir** (application development path), and **area** (encrypted level). It also provides basic methods such as **createBundleContext()** and **getApplicationContext()**. The UIAbility component and ExtensionAbility derived class components have their own **Context** classes, for example, the base class **Context**, **ApplicationContext**, **AbilityStageContext**, **UIAbilityContext**, **ExtensionContext**, and **ServiceExtensionContext**. [Context](../reference/apis/js-apis-inner-application-context.md) is the context of an object in an application. It provides basic information about the application, for example, **resourceManager**, **applicationInfo**, **dir** (application development path), and **area** (encrypted level). It also provides basic methods such as **createBundleContext()** and **getApplicationContext()**. The UIAbility component and ExtensionAbility derived class components have their own **Context** classes, for example, the base class **Context**, **ApplicationContext**, **AbilityStageContext**, **UIAbilityContext**, **ExtensionContext**, and **ServiceExtensionContext**.
- The figure below illustrates the inheritance relationship of contexts. - The figure below illustrates the inheritance relationship of contexts.
![context-inheritance](figures/context-inheritance.png) ![context-inheritance](figures/context-inheritance.png)
- The figure below illustrates the holding relationship of contexts. - The figure below illustrates the holding relationship of contexts.
![context-holding](figures/context-holding.png) ![context-holding](figures/context-holding.png)
- The following describes the information provided by different contexts. The following describes the information provided by different contexts.
- [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md): Each UIAbility has the **Context** attribute, which provides APIs to operate an application component, obtain the application component configuration, and more. - [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md): Each UIAbility has the **Context** attribute, which provides APIs to operate an application component, obtain the application component configuration, and more.
```ts ```ts
...@@ -21,7 +18,7 @@ ...@@ -21,7 +18,7 @@
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
onCreate(want, launchParam) { onCreate(want, launchParam) {
let uiAbilityContext = this.context; let uiAbilityContext = this.context;
// ... ...
} }
} }
``` ```
...@@ -36,7 +33,7 @@ ...@@ -36,7 +33,7 @@
export default class MyService extends ServiceExtensionAbility { export default class MyService extends ServiceExtensionAbility {
onCreate(want) { onCreate(want) {
let serviceExtensionContext = this.context; let serviceExtensionContext = this.context;
// ... ...
} }
} }
``` ```
...@@ -47,7 +44,7 @@ ...@@ -47,7 +44,7 @@
export default class MyAbilityStage extends AbilityStage { export default class MyAbilityStage extends AbilityStage {
onCreate() { onCreate() {
let abilityStageContext = this.context; let abilityStageContext = this.context;
// ... ...
} }
} }
``` ```
...@@ -58,7 +55,7 @@ ...@@ -58,7 +55,7 @@
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
onCreate(want, launchParam) { onCreate(want, launchParam) {
let applicationContext = this.context.getApplicationContext(); let applicationContext = this.context.getApplicationContext();
// ... ...
} }
} }
``` ```
...@@ -85,12 +82,12 @@ The following table describes the application development paths obtained from co ...@@ -85,12 +82,12 @@ The following table describes the application development paths obtained from co
| Name| Type| Readable| Writable| Description| | Name| Type| Readable| Writable| Description|
| -------- | -------- | -------- | -------- | -------- | | -------- | -------- | -------- | -------- | -------- |
| bundleCodeDir | string | Yes | No | Path for storing the application's installation package, that is, installation directory of the application on the internal storage. | | bundleCodeDir | string | Yes | No | Path for storing the application's installation package, that is, installation directory of the application on the internal storage. |
| cacheDir | string | Yes| No| Path for storing the application's cache files, that is, cache directory of the application on the internal storage.<br>It is the content of **Storage** of an application under **Settings > Apps & services > Apps**.| | cacheDir | string | Yes| No| Path for storing the cache files, that is, cache directory of the application on the internal storage.<br>It is the content of **Storage** of an application under **Settings > Apps & services > Apps**.|
| filesDir | string | Yes | No | Path for storing the application's common files, that is, file directory of the application on the internal storage.<br>Files in this directory may be synchronized to other directories during application migration or backup.| | filesDir | string | Yes | No | Path for storing the common files, that is, file directory of the application on the internal storage.<br>Files in this directory may be synchronized to other directories during application migration or backup.|
| preferencesDir | string | Yes | Yes | Path for storing the application's preference files, that is, preferences directory of the application. | | preferencesDir | string | Yes | Yes | Path for storing the preference files, that is, preferences directory of the application. |
| tempDir | string | Yes | No | Path for storing the application's temporary files.<br>Files in this directory are deleted after the application is uninstalled.| | tempDir | string | Yes | No | Path for storing the temporary files.<br>Files in this directory are deleted after the application is uninstalled.|
| databaseDir | string | Yes | No | Path for storing the application's database, that is, storage directory of the local database. | | databaseDir | string | Yes | No | Path for storing the application's database, that is, storage directory of the local database. |
| distributedFilesDir | string | Yes| No| Path for storing the application's distributed files.| | distributedFilesDir | string | Yes| No| Path for storing the distributed files.|
The capability of obtaining the application development path is provided by the base class **Context**. This capability is also provided by **ApplicationContext**, **AbilityStageContext**, **UIAbilityContext**, and **ExtensionContext**. However, the paths obtained from different contexts may differ, as shown below. The capability of obtaining the application development path is provided by the base class **Context**. This capability is also provided by **ApplicationContext**, **AbilityStageContext**, **UIAbilityContext**, and **ExtensionContext**. However, the paths obtained from different contexts may differ, as shown below.
...@@ -135,7 +132,7 @@ export default class EntryAbility extends UIAbility { ...@@ -135,7 +132,7 @@ export default class EntryAbility extends UIAbility {
let bundleCodeDir = this.context.bundleCodeDir; let bundleCodeDir = this.context.bundleCodeDir;
let distributedFilesDir = this.context.distributedFilesDir; let distributedFilesDir = this.context.distributedFilesDir;
let preferencesDir = this.context.preferencesDir; let preferencesDir = this.context.preferencesDir;
// ... ...
} }
} }
``` ```
...@@ -148,7 +145,7 @@ export default class EntryAbility extends UIAbility { ...@@ -148,7 +145,7 @@ export default class EntryAbility extends UIAbility {
Encrypting application files enhances data security by preventing files from unauthorized access. Different application files require different levels of protection. For private files, such as alarms and wallpapers, the application must place them in a directory with the device-level encryption (EL1) to ensure that they can be accessed before the user enters the password. For sensitive files, such as personal privacy data, the application must place them in a directory with the user-level encryption (EL2). Encrypting application files enhances data security by preventing files from unauthorized access. Different application files require different levels of protection. For private files, such as alarms and wallpapers, the application must place them in a directory with the device-level encryption (EL1) to ensure that they can be accessed before the user enters the password. For sensitive files, such as personal privacy data, the application must place them in a directory with the user-level encryption (EL2).
In practice, you need to select a proper encrypted level based on scenario-specific requirements to protect application data security. The proper use of EL1 and the EL2 can efficiently improve the security. In practice, you need to select a proper encryption level based on scenario-specific requirements to protect application data security. The proper use of EL1 and the EL2 can efficiently improve the security.
> **NOTE** > **NOTE**
> >
...@@ -187,13 +184,13 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../ ...@@ -187,13 +184,13 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../
> **NOTE** > **NOTE**
> >
> To obtain the context of another application: > To obtain the context of another application:
> >
> - Request the **ohos.permission.GET_BUNDLE_INFO_PRIVILEGED** permission. For details, see [Declaring Permissions in the Configuration File](../security/accesstoken-guidelines.md#declaring-permissions-in-the-configuration-file). > - Request the **ohos.permission.GET_BUNDLE_INFO_PRIVILEGED** permission. For details, see [Declaring Permissions in the Configuration File](../security/accesstoken-guidelines.md#declaring-permissions-in-the-configuration-file).
> >
> - This is a system API and cannot be called by third-party applications. > - This is a system API and cannot be called by third-party applications.
For example, application information displayed on the home screen includes the application name and icon. The home screen application calls the foregoing method to obtain the context information, so as to obtain the resource information including the application name and icon. For example, application information displayed on the home screen includes the application name and icon. The home screen application calls the foregoing method to obtain the context information, so as to obtain the resource information including the application name and icon.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility'; import UIAbility from '@ohos.app.ability.UIAbility';
...@@ -202,7 +199,7 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../ ...@@ -202,7 +199,7 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../
let bundleName2 = 'com.example.application'; let bundleName2 = 'com.example.application';
let context2 = this.context.createBundleContext(bundleName2); let context2 = this.context.createBundleContext(bundleName2);
let label2 = context2.applicationInfo.label; let label2 = context2.applicationInfo.label;
// ... ...
} }
} }
``` ```
...@@ -224,7 +221,7 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../ ...@@ -224,7 +221,7 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../
let bundleName2 = 'com.example.application'; let bundleName2 = 'com.example.application';
let moduleName2 = 'module1'; let moduleName2 = 'module1';
let context2 = this.context.createModuleContext(bundleName2, moduleName2); let context2 = this.context.createModuleContext(bundleName2, moduleName2);
// ... ...
} }
} }
``` ```
...@@ -238,7 +235,7 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../ ...@@ -238,7 +235,7 @@ The base class **Context** provides [createBundleContext(bundleName:string)](../
onCreate(want, launchParam) { onCreate(want, launchParam) {
let moduleName2 = 'module1'; let moduleName2 = 'module1';
let context2 = this.context.createModuleContext(moduleName2); let context2 = this.context.createModuleContext(moduleName2);
// ... ...
} }
} }
``` ```
...@@ -266,53 +263,53 @@ export default class EntryAbility extends UIAbility { ...@@ -266,53 +263,53 @@ export default class EntryAbility extends UIAbility {
let abilityLifecycleCallback = { let abilityLifecycleCallback = {
// Called when a UIAbility is created. // Called when a UIAbility is created.
onAbilityCreate(uiAbility) { onAbilityCreate(uiAbility) {
console.log(TAG, `onAbilityCreate uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onAbilityCreate uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
}, },
// Called when a window is created. // Called when a window is created.
onWindowStageCreate(uiAbility, windowStage: window.WindowStage) { onWindowStageCreate(uiAbility, windowStage: window.WindowStage) {
console.log(TAG, `onWindowStageCreate uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onWindowStageCreate uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
console.log(TAG, `onWindowStageCreate windowStage: ${JSON.stringify(windowStage)}`); console.info(TAG, `onWindowStageCreate windowStage: ${JSON.stringify(windowStage)}`);
}, },
// Called when the window becomes active. // Called when the window becomes active.
onWindowStageActive(uiAbility, windowStage: window.WindowStage) { onWindowStageActive(uiAbility, windowStage: window.WindowStage) {
console.log(TAG, `onWindowStageActive uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onWindowStageActive uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
console.log(TAG, `onWindowStageActive windowStage: ${JSON.stringify(windowStage)}`); console.info(TAG, `onWindowStageActive windowStage: ${JSON.stringify(windowStage)}`);
}, },
// Called when the window becomes inactive. // Called when the window becomes inactive.
onWindowStageInactive(uiAbility, windowStage: window.WindowStage) { onWindowStageInactive(uiAbility, windowStage: window.WindowStage) {
console.log(TAG, `onWindowStageInactive uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onWindowStageInactive uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
console.log(TAG, `onWindowStageInactive windowStage: ${JSON.stringify(windowStage)}`); console.info(TAG, `onWindowStageInactive windowStage: ${JSON.stringify(windowStage)}`);
}, },
// Called when the window is destroyed. // Called when the window is destroyed.
onWindowStageDestroy(uiAbility, windowStage: window.WindowStage) { onWindowStageDestroy(uiAbility, windowStage: window.WindowStage) {
console.log(TAG, `onWindowStageDestroy uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onWindowStageDestroy uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
console.log(TAG, `onWindowStageDestroy windowStage: ${JSON.stringify(windowStage)}`); console.info(TAG, `onWindowStageDestroy windowStage: ${JSON.stringify(windowStage)}`);
}, },
// Called when the UIAbility is destroyed. // Called when the UIAbility is destroyed.
onAbilityDestroy(uiAbility) { onAbilityDestroy(uiAbility) {
console.log(TAG, `onAbilityDestroy uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onAbilityDestroy uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
}, },
// Called when the UIAbility is switched from the background to the foreground. // Called when the UIAbility is switched from the background to the foreground.
onAbilityForeground(uiAbility) { onAbilityForeground(uiAbility) {
console.log(TAG, `onAbilityForeground uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onAbilityForeground uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
}, },
// Called when the UIAbility is switched from the foreground to the background. // Called when the UIAbility is switched from the foreground to the background.
onAbilityBackground(uiAbility) { onAbilityBackground(uiAbility) {
console.log(TAG, `onAbilityBackground uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onAbilityBackground uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
}, },
// Called when UIAbility is continued on another device. // Called when UIAbility is continued on another device.
onAbilityContinue(uiAbility) { onAbilityContinue(uiAbility) {
console.log(TAG, `onAbilityContinue uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`); console.info(TAG, `onAbilityContinue uiAbility.launchWant: ${JSON.stringify(uiAbility.launchWant)}`);
} }
} }
// Obtain the application context. // Obtain the application context.
let applicationContext = this.context.getApplicationContext(); let applicationContext = this.context.getApplicationContext();
// Register the application lifecycle callback. // Register the application lifecycle callback.
this.lifecycleId = applicationContext.on('abilityLifecycle', abilityLifecycleCallback); this.lifecycleId = applicationContext.on('abilityLifecycle', abilityLifecycleCallback);
console.log(TAG, `register callback number: ${this.lifecycleId}`); console.info(TAG, `register callback number: ${this.lifecycleId}`);
} }
// ... ...
onDestroy() { onDestroy() {
// Obtain the application context. // Obtain the application context.
......
...@@ -12,10 +12,9 @@ Along its evolution, OpenHarmony has provided two application models: ...@@ -12,10 +12,9 @@ Along its evolution, OpenHarmony has provided two application models:
The stage model is designed based on the following considerations, which make it become the recommended model: The stage model is designed based on the following considerations, which make it become the recommended model:
1. **Designed for complex applications** 1. **Designed for complex applications**
- In the stage model, multiple application components share an ArkTS engine (VM running the programming language ArkTS) instance, making it easy for application components to share objects and status while requiring less memory. - In the stage model, multiple application components share an ArkTS engine (VM running the programming language ArkTS) instance, making it easy for application components to share objects and status while requiring less memory.
- The object-oriented development mode makes the code of complex applications easy to read, maintain, and scale. - The object-oriented development mode makes the code of complex applications easy to read, maintain, and scale.
2. **Native support for [cross-device migration](hop-cross-device-migration.md) and [multi-device collaboration](hop-multi-device-collaboration.md) at the application component level** 2. **Native support for [cross-device migration](hop-cross-device-migration.md) and [multi-device collaboration](hop-multi-device-collaboration.md) at the application component level**
The stage model decouples application components from User Interfaces (UIs). The stage model decouples application components from User Interfaces (UIs).
...@@ -38,7 +37,7 @@ The stage model is designed based on the following considerations, which make it ...@@ -38,7 +37,7 @@ The stage model is designed based on the following considerations, which make it
The stage model redefines the boundary of application capabilities to well balance application capabilities and system management costs. The stage model redefines the boundary of application capabilities to well balance application capabilities and system management costs.
- Diverse application components (such as widgets and input methods) for specific scenarios. - Diverse application components (such as service widgets and input methods) for specific scenarios.
- Standardized background process management. To deliver a better user experience, the stage model manages background application processes in a more orderly manner. Applications cannot reside in the background randomly, and their background behavior is strictly managed to minimize malicious behavior. - Standardized background process management. To deliver a better user experience, the stage model manages background application processes in a more orderly manner. Applications cannot reside in the background randomly, and their background behavior is strictly managed to minimize malicious behavior.
...@@ -52,8 +51,8 @@ The table below describes their differences in detail. ...@@ -52,8 +51,8 @@ The table below describes their differences in detail.
| Item| FA model| Stage model| | Item| FA model| Stage model|
| -------- | -------- | -------- | | -------- | -------- | -------- |
| **Application component**| 1. Component classification<br>![fa-model-component](figures/fa-model-component.png)<br/>- PageAbility: has the UI and supports user interaction For details, see [PageAbility Component Overview](pageability-overview.md).<br>- ServiceAbility: provides background services and has no UI. For details, see [ServiceAbility Component Overview](serviceability-overview.md).<br>- DataAbility: provides the data sharing capability and has no UI. For details, see [DataAbility Component Overview](dataability-overview.md).<br>2. Development mode<br>Application components are specified by exporting anonymous objects and fixed entry files. You cannot perform derivation. It is inconvenient for capability expansion. | 1. Component classification<br>![stage-model-component](figures/stage-model-component.png)<br/> - UIAbility: has the UI and supports user interaction. For details, see [UIAbility Component Overview](uiability-overview.md).<br>- ExtensionAbility: provides extension capabilities (such as widget and input methods) for specific scenarios. For details, see [ExtensionAbility Component Overview](extensionability-overview.md).<br>2. Development mode<br>The object-oriented mode is used to provide open application components as classes. You can derive application components for capability expansion. | | **Application component**| 1. Component classification<br>![fa-model-component](figures/fa-model-component.png)<br>- PageAbility: has the UI and supports user interaction For details, see [PageAbility Component Overview](pageability-overview.md).<br>- ServiceAbility: provides background services and has no UI. For details, see [ServiceAbility Component Overview](serviceability-overview.md).<br>- DataAbility: provides the data sharing capability and has no UI. For details, see [DataAbility Component Overview](dataability-overview.md).<br>2. Development mode<br>Application components are specified by exporting anonymous objects and fixed entry files. You cannot perform derivation. It is inconvenient for capability expansion.| 1. Component classification<br>![stage-model-component](figures/stage-model-component.png)<br>- UIAbility: has the UI and supports user interaction. For details, see [UIAbility Component Overview](uiability-overview.md).<br>- ExtensionAbility: provides extension capabilities (such as widget and input methods) for specific scenarios. For details, see [ExtensionAbility Component Overview](extensionability-overview.md).<br>2. Development mode<br>The object-oriented mode is used to provide open application components as classes. You can derive application components for capability expansion.|
| **Process model**| There are two types of processes:<br>1. Main process<br>2. Rendering process<br>For details, see [Process Model (FA Model)](process-model-fa.md).| There are three types of processes:<br>1. Main process<br>2. ExtensionAbility process<br>3. Rendering process<br>For details, see [Process Model (Stage Model)](process-model-stage.md).| | **Process model**| There are two types of processes:<br>1. Main process<br>2. Rendering process<br>For details, see [Process Model Overview (FA Model)](process-model-fa.md). | There are three types of processes:<br>1. Main process<br>2. ExtensionAbility process<br>3. Rendering process<br>For details, see [Process Model Overview (Stage Model)](process-model-stage.md). |
| **Thread model**| 1. ArkTS engine instance creation<br>A process can run multiple application component instances, and each application component instance runs in an independent ArkTS engine instance.<br>2. Thread model<br>Each ArkTS engine instance is created on an independent thread (non-main thread). The main thread does not have an ArkTS engine instance.<br>3. Intra-process object sharing: not supported.<br>For details, see [Thread Model (FA Model)](thread-model-fa.md).| 1. ArkTS engine instance creation<br>A process can run multiple application component instances, and all application component instances share one ArkTS engine instance.<br>2. Thread model<br>The ArkTS engine instance is created on the main thread.<br>3. Intra-process object sharing: supported.<br>For details, see [Thread Model (Stage Model)](thread-model-stage.md).| | **Thread model**| 1. ArkTS engine instance creation<br>A process can run multiple application component instances, and each application component instance runs in an independent ArkTS engine instance.<br>2. Thread model<br>Each ArkTS engine instance is created on an independent thread (non-main thread). The main thread does not have an ArkTS engine instance.<br>3. Intra-process object sharing: not supported.<br>For details, see [Thread Model Overview (FA Model)](thread-model-fa.md). | 1. ArkTS engine instance creation<br>A process can run multiple application component instances, and all application component instances share one ArkTS engine instance.<br>2. Thread model<br>The ArkTS engine instance is created on the main thread.<br>3. Intra-process object sharing: supported.<br>For details, see [Thread Model Overview (Stage Model)](thread-model-stage.md). |
| **Mission management model**| - A mission is created for each PageAbility component instance.<br>- Missions are stored persistently until the number of missions exceeds the maximum (customized based on the product configuration) or users delete missions.<br>- PageAbility components do not form a stack structure.<br>For details, see [Mission Management Scenarios](mission-management-overview.md).| - A mission is created for each UIAbility component instance.<br>- Missions are stored persistently until the number of missions exceeds the maximum (customized based on the product configuration) or users delete missions.<br>- UIAbility components do not form a stack structure.<br>For details, see [Mission Management Scenarios](mission-management-overview.md).| | **Mission management model**| - A mission is created for each PageAbility component instance.<br>- Missions are stored persistently until the number of missions exceeds the maximum (customized based on the product configuration) or users delete missions.<br>- PageAbility components do not form a stack structure.<br>For details, see [Mission Management Scenarios](mission-management-overview.md).| - A mission is created for each UIAbility component instance.<br>- Missions are stored persistently until the number of missions exceeds the maximum (customized based on the product configuration) or users delete missions.<br>- UIAbility components do not form a stack structure.<br>For details, see [Mission Management Scenarios](mission-management-overview.md).|
| **Application configuration file**| The **config.json** file is used to describe the application, HAP, and application component information.<br>For details, see [Application Configuration File Overview (FA Model)](../quick-start/application-configuration-file-overview-fa.md).| The **app.json5** file is used to describe the application information, and the **module.json5** file is used to describe the HAP and application component information.<br>For details, see [Application Configuration File Overview (Stage Model)](../quick-start/application-configuration-file-overview-stage.md).| | **Application configuration file**| The **config.json** file is used to describe the application, HAP, and application component information.<br>For details, see [Application Configuration File Overview (FA Model)](../quick-start/application-configuration-file-overview-fa.md).| The **app.json5** file is used to describe the application information, and the **module.json5** file is used to describe the HAP and application component information.<br>For details, see [Application Configuration File Overview (Stage Model)](../quick-start/application-configuration-file-overview-stage.md).|
...@@ -23,8 +23,8 @@ In view of this, OpenHarmony formulates a set of component startup rules, as fol ...@@ -23,8 +23,8 @@ In view of this, OpenHarmony formulates a set of component startup rules, as fol
- **Before starting a component of another application, verify the visible field of the target component.** - **Before starting a component of another application, verify the visible field of the target component.**
- If the **visible** field of the target component is **false**, verify the **ohos.permission.START_INVISIBLE_ABILITY** permission. - If the **exported** field of the target component is **false**, verify the **ohos.permission.START_INVISIBLE_ABILITY** permission.
- For details, see [Component Visible Configuration](../quick-start/module-configuration-file.md#abilities). - For details, see [Component exported Configuration](../quick-start/module-configuration-file.md#abilities).
- **Before starting a component of a background application, verify the BACKGROUND permission.** - **Before starting a component of a background application, verify the BACKGROUND permission.**
- An application is considered as a foreground application only when the application process gains focus or its UIAbility component is running in the foreground. - An application is considered as a foreground application only when the application process gains focus or its UIAbility component is running in the foreground.
...@@ -37,8 +37,8 @@ In view of this, OpenHarmony formulates a set of component startup rules, as fol ...@@ -37,8 +37,8 @@ In view of this, OpenHarmony formulates a set of component startup rules, as fol
> **NOTE** > **NOTE**
> >
> - Component startup control has been implemented since OpenHarmony v3.2 Release. > - Component startup control has been implemented since OpenHarmony v3.2 Release.
> >
> - The new component startup rules are more strict than the original ones. You must be familiar with the new startup rules to prevent service exceptions. > - The new component startup rules are more strict than the original ones. You must be familiar with the new startup rules to prevent service exceptions.
## Intra-Device Component Startup Rules ## Intra-Device Component Startup Rules
......
...@@ -30,7 +30,7 @@ export default { ...@@ -30,7 +30,7 @@ export default {
``` ```
After the PageAbility is created, its abilities-related configuration items are displayed in the **config.json** file. The following is an example **config.json** file of an ability named MainAbility: After the PageAbility is created, its abilities-related configuration items are displayed in the **config.json** file. The following is an example **config.json** file of an ability named EntryAbility:
```json ```json
{ {
...@@ -48,13 +48,13 @@ After the PageAbility is created, its abilities-related configuration items are ...@@ -48,13 +48,13 @@ After the PageAbility is created, its abilities-related configuration items are
], ],
"orientation": "unspecified", "orientation": "unspecified",
"visible": true, "visible": true,
"srcPath": "MainAbility", "srcPath": "EntryAbility",
"name": ".MainAbility", "name": ".EntryAbility",
"srcLanguage": "ets", "srcLanguage": "ets",
"icon": "$media:icon", "icon": "$media:icon",
"description": "$string:MainAbility_desc", "description": "$string:EntryAbility_desc",
"formsEnabled": false, "formsEnabled": false,
"label": "$string:MainAbility_label", "label": "$string:EntryAbility_label",
"type": "page", "type": "page",
"launchType": "singleton" "launchType": "singleton"
} }
......
...@@ -48,9 +48,9 @@ function implicitStartAbility() { ...@@ -48,9 +48,9 @@ function implicitStartAbility() {
} }
} }
context.startAbility(wantInfo).then(() => { context.startAbility(wantInfo).then(() => {
// ... ...
}).catch((err) => { }).catch((err) => {
// ... ...
}) })
} }
``` ```
...@@ -66,9 +66,8 @@ In the preceding code, under the custom field **parameters**, the following **ab ...@@ -66,9 +66,8 @@ In the preceding code, under the custom field **parameters**, the following **ab
- **ability.picker.fileSizes**: file size, in bytes. - **ability.picker.fileSizes**: file size, in bytes.
- **ability.picker.fileNames** and **ability.picker.fileSizes** are arrays and have a one-to-one mapping. - **ability.picker.fileNames** and **ability.picker.fileSizes** are arrays and have a one-to-one mapping.
The following figure shows an example. The following figure shows an example.
![](figures/ability-startup-with-implicit-want2.png)
![stage-want2](figures/stage-want2.png)
## Shared Party ## Shared Party
...@@ -77,17 +76,17 @@ To enable the shared party to identify the shared content, configure **skills** ...@@ -77,17 +76,17 @@ To enable the shared party to identify the shared content, configure **skills**
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
// ... ...
"skills": [ "skills": [
{ {
// ... ...
"actions": [ "actions": [
"action.system.home", "action.system.home",
"ohos.want.action.sendData" "ohos.want.action.sendData"
// ... ...
], ],
"uris": [ "uris": [
{ {
...@@ -102,7 +101,7 @@ To enable the shared party to identify the shared content, configure **skills** ...@@ -102,7 +101,7 @@ To enable the shared party to identify the shared content, configure **skills**
} }
``` ```
After the user selects an application, the Want nested in the **ability.want.params.INTENT** field is passed to that application. The UIAbility of the shared party, after being started, can call [onCreate()](../reference/apis/js-apis-app-ability-uiAbility.md#uiabilityoncreate) or [onNewWant()](../reference/apis/js-apis-app-ability-uiAbility.md#uiabilityonnewwant) to obtain the passed Want. After the user selects an application, the Want nested in the **ability.want.params.INTENT** field is passed to that application. After the UIAbility of the application starts, the application obtains **want** information from [**onCreate()**](../reference/apis/js-apis-app-ability-uiAbility.md#uiabilityoncreate) or [**onNewWant()**](../reference/apis/js-apis-app-ability-uiAbility.md#uiabilityonnewwant).
The following is an example of the Want obtained. You can use the FD of the shared file to perform required operations. The following is an example of the Want obtained. You can use the FD of the shared file to perform required operations.
......
# Matching Rules of Explicit Want and Implicit Want # Matching Rules of Explicit Want and Implicit Want
Both explicit Want and implicit Want can be used to match an ability to start based on certain rules. These rules determine how the parameters set in Want match the configuration file declared by the target ability. Both explicit [Want](../reference/apis/js-apis-app-ability-want.md) and implicit [Want](../reference/apis/js-apis-app-ability-want.md) can be used to match an application component to start based on certain rules. These rules determine how the parameters set in [want](../reference/apis/js-apis-app-ability-want.md) match the configuration file declared by the target application component.
## Matching Rules of Explicit Want ## Matching Rules of Explicit Want
The table below describes the matching rules of explicit [Want](../reference/apis/js-apis-app-ability-want.md).
| Name| Type| Matching Item| Mandatory| Rule Description| | Name| Type| Matching Item| Mandatory| Rule Description|
| -------- | -------- | -------- | -------- | -------- | | -------- | -------- | -------- | -------- | -------- |
| deviceId | string | Yes| No| If this field is unspecified, only abilities on the local device are matched.| | deviceId | string | Yes| No| If this field is unspecified, only application components on the local device are matched.|
| bundleName | string | Yes| Yes| If **abilityName** is specified but **bundleName** is unspecified, the matching fails.| | bundleName | string | Yes| Yes| If **abilityName** is specified but **bundleName** is unspecified, the matching fails.|
| moduleName | string | Yes| No| If this field is unspecified and multiple modules with the same ability name exist in the application, the first ability is matched by default.| | moduleName | string | Yes| No| If this field is unspecified and multiple modules with the same ability name exist in the application, the first application component is matched by default.|
| abilityName | string | Yes| Yes| To use explicit Want, this field must be specified.| | abilityName | string | Yes| Yes| To use explicit Want, this field must be specified.|
| uri | string | No| No| This field is not used for matching. It is passed to the target ability as a parameter.| | uri | string | No| No| This field is not used for matching. It is passed to the target application component as a parameter.|
| type | string | No| No| This field is not used for matching. It is passed to the target ability as a parameter.| | type | string | No| No| This field is not used for matching. It is passed to the target application component as a parameter.|
| action | string | No| No| This field is not used for matching. It is passed to the target ability as a parameter.| | action | string | No| No| This field is not used for matching. It is passed to the target application component as a parameter.|
| entities | Array&lt;string&gt; | No| No| This field is not used for matching. It is passed to the target ability as a parameter.| | entities | Array&lt;string&gt; | No| No| This field is not used for matching. It is passed to the target application component as a parameter.|
| flags | number | No| No| This field is not used for matching and is directly transferred to the system for processing. It is generally used to set runtime information, such as URI data authorization.| | flags | number | No| No| This field is not used for matching and is directly transferred to the system for processing. It is generally used to set runtime information, such as URI data authorization.|
| parameters | {[key:&nbsp;string]:&nbsp;any} | No| No| This field is not used for matching. It is passed to the target ability as a parameter.| | parameters | {[key:&nbsp;string]:&nbsp;any} | No| No| This field is not used for matching. It is passed to the target application component as a parameter.|
## Matching Rules for Implicit Want
## Matching Rules of Implicit Want The table below describes the matching rules of implicit [Want](../reference/apis/js-apis-app-ability-want.md).
| Name | Type | Matching Item| Mandatory| Rule Description | | Name | Type | Matching Item| Mandatory| Rule Description |
| ----------- | ------------------------------ | ------ | ---- | ------------------------------------------------------------ | | ----------- | ------------------------------ | ------ | ---- | ------------------------------------------------------------ |
...@@ -30,31 +35,32 @@ Both explicit Want and implicit Want can be used to match an ability to start ba ...@@ -30,31 +35,32 @@ Both explicit Want and implicit Want can be used to match an ability to start ba
| action | string | Yes | No | | | action | string | Yes | No | |
| entities | Array&lt;string&gt; | Yes | No | | | entities | Array&lt;string&gt; | Yes | No | |
| flags | number | No | No | This field is not used for matching and is directly transferred to the system for processing. It is generally used to set runtime information, such as URI data authorization.| | flags | number | No | No | This field is not used for matching and is directly transferred to the system for processing. It is generally used to set runtime information, such as URI data authorization.|
| parameters | {[key:&nbsp;string]:&nbsp;any} | No | No | This field is not used for matching. It is passed to the target ability as a parameter. | | parameters | {[key:&nbsp;string]:&nbsp;any} | No | No | This field is not used for matching. It is passed to the target application component as a parameter. |
## Interpretation of Implicit Want Matching Rules
Get familiar with the following about implicit Want: Get familiar with the following about implicit Want:
- The **want** parameter passed by the caller indicates the operation to be performed by the caller. It also provides data and application type restrictions. - The **want** parameter passed by the caller indicates the operation to be performed by the caller. It also provides data and application type restrictions.
- The **skills** field declares the capabilities of the target ability. For details, see [the skills tag](../quick-start/module-configuration-file.md#skills) in the [module.json5 file](../quick-start/module-configuration-file.md). - The **skills** field declares the capabilities of the target application component. For details, see [the skills tag](../quick-start/module-configuration-file.md#skills) in the [module.json5 file](../quick-start/module-configuration-file.md).
The system matches the **want** parameter (including the **action**, **entities**, **uri**, and **type** attributes) passed by the caller against the **skills** configuration (including the **actions**, **entities**, **uris**, and **type** attributes) of the abilities one by one. When all the four attributes are matched, a dialog box is displayed for users to select a matched application. The system matches the **want** parameter (including the **action**, **entities**, **uri**, and **type** attributes) passed by the caller against the **skills** configuration (including the **actions**, **entities**, **uris**, and **type** attributes) of the application components one by one. When all the four attributes are matched, a dialog box is displayed for users to select a matched application.
### Matching Rules of action in the want Parameter ### Matching Rules of action in the want Parameter
The system matches the **action** attribute in the **want** parameter passed by the caller against **actions** under **skills** of the abilities. The system matches the **action** attribute in the **want** parameter passed by the caller against **actions** under **skills** of the application components.
- If **action** in the passed **want** parameter is unspecified and **actions** under **skills** of an application component is unspecified, the matching fails.
- If **action** in the passed **want** parameter is specified but **actions** under **skills** of an ability is unspecified, the matching fails. - If **action** in the passed **want** parameter is specified but **actions** under **skills** of an application component is unspecified, the matching fails.
- If **action** in the passed **want** parameter is unspecified but **actions** under **skills** of an ability is specified, the matching is successful. - If **action** in the passed **want** parameter is unspecified but **actions** under **skills** of an application component is specified, the matching is successful.
- If **action** in the passed **want** parameter is specified, and **actions** under **skills** of an ability is specified and contains **action** in the passed **want** parameter, the matching is successful. - If **action** in the passed **want** parameter is specified, and **actions** under **skills** of an application component is specified and contains **action** in the passed **want** parameter, the matching is successful.
- If **action** in the passed **want** parameter is specified, and **actions** under **skills** of an ability is specified but does not contain **action** in the passed **want** parameter, the matching fails. - If **action** in the passed **want** parameter is specified, and **actions** under **skills** of an application component is specified but does not contain **action** in the passed **want** parameter, the matching fails.
**Figure 1** Matching rules of action in the want parameter **Figure 1** Matching rules of action in the want parameter
...@@ -63,55 +69,56 @@ The system matches the **action** attribute in the **want** parameter passed by ...@@ -63,55 +69,56 @@ The system matches the **action** attribute in the **want** parameter passed by
### Matching Rules of entities in the want Parameter ### Matching Rules of entities in the want Parameter
The system matches the **entities** attribute in the **want** parameter passed by the caller against **entities** under **skills** of the abilities. The system matches the **entities** attribute in the **want** parameter passed by the caller against **entities** under **skills** of the application components.
- If **entities** in the passed **want** parameter is unspecified but **entities** under **skills** of an ability is specified, the matching is successful. - If **entities** in the passed **want** parameter is unspecified but **entities** under **skills** of an application component is specified, the matching is successful.
- If **entities** in the passed **want** parameter is unspecified but **entities** under **skills** of an ability is unspecified, the matching is successful. - If **entities** in the passed **want** parameter is unspecified but **entities** under **skills** of an application component is unspecified, the matching is successful.
- If **entities** in the passed **want** parameter is specified but **entities** under **skills** of an ability is unspecified, the matching fails. - If **entities** in the passed **want** parameter is specified but **entities** under **skills** of an application component is unspecified, the matching fails.
- If **entities** in the passed **want** parameter is specified, and **entities** under **skills** of an ability is specified and contains **entities** in the passed **want** parameter, the matching is successful. - If **entities** in the passed **want** parameter is specified, and **entities** under **skills** of an application component is specified and contains **entities** in the passed **want** parameter, the matching is successful.
- If **entities** in the passed **want** parameter is specified, and **entities** under **skills** of an ability is specified but does not contain **entities** in the passed **want** parameter, the matching fails. - If **entities** in the passed **want** parameter is specified, and **entities** under **skills** of an application component is specified but does not contain **entities** in the passed **want** parameter, the matching fails.
**Figure 2** Matching rule of entities in the want parameter **Figure 2** Matching rules of entities in the want parameter
![want-entities](figures/want-entities.png) ![want-entities](figures/want-entities.png)
### Matching Rules of uri and type in the want Parameter ### Matching Rules of uri and type in the want Parameter
When the **uri** and **type** parameters are specified in the **want** parameter to initiate a component startup request, the system traverses the list of installed components and matches the **uris** array under **skills** of the abilities one by one. If one of the **uris** arrays under **skills** matches the **uri** and **type** in the passed **want**, the matching is successful. When the **uri** and **type** parameters are specified in the **want** parameter to initiate an application component startup request, the system traverses the list of installed components and matches the **uris** array under **skills** of the application components one by one. If one of the **uris** arrays under **skills** matches the **uri** and **type** in the passed **want**, the matching is successful.
There are four combinations of **uri** and **type** settings. The matching rules are as follows: There are four combinations of **uri** and **type** settings. The matching rules are as follows:
- Neither **uri** or **type** is specified in the **want** parameter. - Neither **uri** or **type** is specified in the **want** parameter.
- If the **uris** array under **skills** of an ability is unspecified, the matching is successful. - If the **uris** array under **skills** of an application component is unspecified, the matching is successful.
- If the **uris** array under **skills** of an ability contains an URI element whose **scheme** and **type** are unspecified, the matching is successful. - If the **uris** array under **skills** of an application component contains an URI element whose **scheme** and **type** are unspecified, the matching is successful.
- In other cases, the matching fails. - In other cases, the matching fails.
- Only **uri** is specified in the **want** parameter. - Only **uri** is specified in the **want** parameter.
- If the **uris** array under **skills** of an ability is unspecified, the matching fails. - If the **uris** array under **skills** of an application component is unspecified, the matching fails.
- If the **uris** array under **skills** of an ability contains an element whose [uri is matched](#matching-rules-of-uri) and **type** is unspecified, the matching is successful. Otherwise, the matching fails. - If the **uris** array under **skills** of an application component contains an element whose [uri is matched](#matching-rules-of-uri) and **type** is unspecified, the matching is successful. Otherwise, the matching fails.
- Only **type** is specified in the **want** parameter. - Only **type** is specified in the **want** parameter.
- If the **uris** array under **skills** of an ability is unspecified, the matching fails. - If the **uris** array under **skills** of an application component is unspecified, the matching fails.
- If the **uris** array under **skills** of an ability contains an URI element whose **scheme** is unspecified and [type is matched](#matching-rules-of-type), the matching is successful. Otherwise, the matching fails. - If the **uris** array under **skills** of an application component contains an URI element whose **scheme** is unspecified and [type is matched](#matching-rules-of-type), the matching is successful. Otherwise, the matching fails.
- Both **uri** and **type** are specified in the **want** parameter, as shown in Figure 3. - Both **uri** and **type** are specified in the **want** parameter, as shown below.
- If the **uris** array under **skills** of an ability is unspecified, the matching fails. - If the **uris** array under **skills** of an application component is unspecified, the matching fails.
- If the **uris** array under **skills** of an ability contains an element whose [uri is matched](#matching-rules-of-uri) and [type is matched](#matching-rules-of-type), the matching is successful. Otherwise, the matching fails. - If the **uris** array under **skills** of an application component contains an element whose [uri is matched](#matching-rules-of-uri) and [type is matched](#matching-rules-of-type), the matching is successful. Otherwise, the matching fails.
Leftmost URI matching: When only **scheme**, a combination of **scheme** and **host**, or a combination of **scheme**, **host**, and **port** is configured in the **uris** array under **skills** of the ability, Leftmost URI matching: When only **scheme**, a combination of **scheme** and **host**, or a combination of **scheme**, **host**, and **port** is configured in the **uris** array under **skills** of the application component, the matching is successful only if the leftmost URI in the passed **want** parameter matches **scheme**, the combination of **scheme** and **host**, or the combination of **scheme**, **host**, and **port**.
the matching is successful only if the leftmost URI in the passed **want** parameter matches **scheme**, the combination of **scheme** and **host**, or the combination of **scheme**, **host**, and **port**.
**Figure 3** Matching rules when uri and type are specified in the want parameter **Figure 3** Matching rules when uri and type are specified in the want parameter
![want-uri-type1](figures/want-uri-type1.png) ![want-uri-type1](figures/want-uri-type1.png)
To simplify the description:
To simplify the description, **uri** and **type** passed in the **want** parameter are called **w_uri** and **w_type**, respectively; the **uris** array under **skills** of an ability to match is called **s_uris**; each element in the array is called **s_uri**. Matching is performed from top to bottom. - **uri** in the **want** parameter passed in by the caller is called **w_uri**; each element in the **uris** array under **skills** of the application component to match is called **s_uri**.
- **type** in the **want** parameter passed in by the caller is called **w_type**; the type in the **uris** array under **skills** of the application component to match is called **s_type**.
**Figure 4** Matching rules of uri and type in the want parameter **Figure 4** Matching rules of uri and type in the want parameter
...@@ -120,7 +127,7 @@ To simplify the description, **uri** and **type** passed in the **want** paramet ...@@ -120,7 +127,7 @@ To simplify the description, **uri** and **type** passed in the **want** paramet
### Matching Rules of uri ### Matching Rules of uri
To simplify the description, **uri** in the passed **want** parameter is called **w_uri**; **uri** under **skills** of an ability to match is called **s_uri**. The matching rules are as follows: The rules are as follows:
- If **scheme** of **s_uri** is unspecified and **w_uri** is unspecified, the matching is successful. Otherwise, the matching fails. - If **scheme** of **s_uri** is unspecified and **w_uri** is unspecified, the matching is successful. Otherwise, the matching fails.
...@@ -138,18 +145,15 @@ To simplify the description, **uri** in the passed **want** parameter is called ...@@ -138,18 +145,15 @@ To simplify the description, **uri** in the passed **want** parameter is called
> **NOTE** > **NOTE**
> >
> The **scheme**, **host**, **port**, **path**, **pathStartWith**, and **pathRegex** attributes of **uris** under **skills** of an ability are concatenated. If **path**, **pathStartWith**, and **pathRegex** are declared in sequence, **uris** can be concatenated into the following expressions: > The **scheme**, **host**, **port**, **path**, **pathStartWith**, and **pathRegex** attributes of **uris** under **skills** of an application component are concatenated. If **path**, **pathStartWith**, and **pathRegex** are declared in sequence, **uris** can be concatenated into the following expressions:
>
> - **Full path expression**: scheme://host:port/path
>
> - **Prefix expression**: scheme://host:port/pathStartWith
>
> - **Regular expression**: scheme://host:port/pathRegex
> >
> - **Prefix URI expression**: When only **scheme**, a combination of **scheme** and **host**, or a combination of **scheme**, **host**, and **port** is configured in the configuration file, the matching is successful if a URI prefixed with the configuration file is passed in. > - **Prefix URI expression**: When only **scheme**, a combination of **scheme** and **host**, or a combination of **scheme**, **host**, and **port** is configured in the configuration file, the matching is successful if a URI prefixed with the configuration file is passed in.
> * `scheme://` > * `scheme://`
> * `scheme://host` > * `scheme://host`
> * `scheme://host:port` > * `scheme://host:port`
> - **Full path expression**: `scheme://host:port/path`
> - **Prefix expression**: `scheme://host:port/pathStartWith`
> - **Regular expression**: `scheme://host:port/pathRegex`
### Matching Rules of type ### Matching Rules of type
...@@ -158,7 +162,7 @@ To simplify the description, **uri** in the passed **want** parameter is called ...@@ -158,7 +162,7 @@ To simplify the description, **uri** in the passed **want** parameter is called
> >
> The matching rules of **type** described in this section are based on the fact that **type** in the **want** parameter is specified. If **type** is unspecified, follow the [matching rules of uri and type in the want parameter](#matching-rules-of-uri-and-type-in-the-want-parameter). > The matching rules of **type** described in this section are based on the fact that **type** in the **want** parameter is specified. If **type** is unspecified, follow the [matching rules of uri and type in the want parameter](#matching-rules-of-uri-and-type-in-the-want-parameter).
To simplify the description, **uri** in the passed **want** parameter is called **w_type**, and **type** of **uris** under **skills** of an ability to match is called **s_type**. The matching rules are as follows: The matching rules are as follows:
- If **s_type** is unspecified, the matching fails. - If **s_type** is unspecified, the matching fails.
......
...@@ -9,9 +9,9 @@ An [ExtensionAbilityType](../reference/apis/js-apis-bundleManager.md#extensionab ...@@ -9,9 +9,9 @@ An [ExtensionAbilityType](../reference/apis/js-apis-bundleManager.md#extensionab
- [FormExtensionAbility](../reference/apis/js-apis-app-form-formExtensionAbility.md): ExtensionAbility component of the form type, which provides APIs related to widgets. - [FormExtensionAbility](../reference/apis/js-apis-app-form-formExtensionAbility.md): ExtensionAbility component of the form type, which provides APIs related to widgets.
- [WorkSchedulerExtensionAbility](../reference/apis/js-apis-WorkSchedulerExtensionAbility.md): ExtensionAbility component of the work_scheduler type, which provides APIs for registering, canceling, and querying Work Scheduler tasks. - [WorkSchedulerExtensionAbility](../reference/apis/js-apis-WorkSchedulerExtensionAbility.md): ExtensionAbility component of the work_scheduler type, which provides callbacks for Work Scheduler tasks.
- [InputMethodExtensionAbility](../reference/apis/js-apis-inputmethod.md): ExtensionAbility component of the input_method type, which provides an input method framework that can be used to hide the keyboard, obtain the list of installed input methods, display the dialog box for input method selection, and more. - [InputMethodExtensionAbility](../reference/apis/js-apis-inputmethod.md): ExtensionAbility component of the input_method type, which is used to develop input method applications.
- [ServiceExtensionAbility](../reference/apis/js-apis-app-ability-serviceExtensionAbility.md): ExtensionAbility component of the service type, which provides APIs related to background service scenarios. - [ServiceExtensionAbility](../reference/apis/js-apis-app-ability-serviceExtensionAbility.md): ExtensionAbility component of the service type, which provides APIs related to background service scenarios.
...@@ -33,6 +33,7 @@ An [ExtensionAbilityType](../reference/apis/js-apis-bundleManager.md#extensionab ...@@ -33,6 +33,7 @@ An [ExtensionAbilityType](../reference/apis/js-apis-bundleManager.md#extensionab
> >
> 3. Third-party applications can use other types of ExtensionAbility components that have been defined. > 3. Third-party applications can use other types of ExtensionAbility components that have been defined.
## Using ExtensionAbility of the Specified Type ## Using ExtensionAbility of the Specified Type
All types of ExtensionAbility components are started by the corresponding system management service, rather than applications, so that their lifecycles are under control by the system. The caller of the ExtensionAbility component does not need to care about its lifecycle. All types of ExtensionAbility components are started by the corresponding system management service, rather than applications, so that their lifecycles are under control by the system. The caller of the ExtensionAbility component does not need to care about its lifecycle.
...@@ -49,20 +50,17 @@ The following uses [InputMethodExtensionAbility](../reference/apis/js-apis-input ...@@ -49,20 +50,17 @@ The following uses [InputMethodExtensionAbility](../reference/apis/js-apis-input
The following uses [FormExtensionAbility](../reference/apis/js-apis-app-form-formExtensionAbility.md) as an example. The widget framework provides the base class [FormExtensionAbility](../reference/apis/js-apis-app-form-formExtensionAbility.md). You derive this base class to create your own class (such as **MyFormExtensionAbility**), implement the callbacks, such as **onCreate()** and **onUpdateForm()**, to provide specific widget functionalities. For details, see [FormExtensionAbility](service-widget-overview.md). The following uses [FormExtensionAbility](../reference/apis/js-apis-app-form-formExtensionAbility.md) as an example. The widget framework provides the base class [FormExtensionAbility](../reference/apis/js-apis-app-form-formExtensionAbility.md). You derive this base class to create your own class (such as **MyFormExtensionAbility**), implement the callbacks, such as **onCreate()** and **onUpdateForm()**, to provide specific widget functionalities. For details, see [FormExtensionAbility](service-widget-overview.md).
You do not need to care when to add or delete a widget. The lifecycle of the FormExtensionAbility instance and the lifecycle of the ExtensionAbility process where the FormExtensionAbility instance is located are scheduled and managed by FormManagerService. You do not need to care when to add or delete a widget. The lifecycle of the FormExtensionAbility instance and the lifecycle of the ExtensionAbility process where the FormExtensionAbility instance is located are scheduled and managed by FormManagerService.
![form_extension](figures/form_extension.png) ![form_extension](figures/form_extension.png)
> **NOTE** > **NOTE**
> >
> For an application, all ExtensionAbility components of the same type run in an independent process, whereas UIAbility, ServiceExtensionAbility, and DataShareExtensionAbility run in another independent process. For details, see [Process Model (Stage Model)](process-model-stage.md). > For an application, all ExtensionAbility components of the same type run in an independent process, whereas UIAbility, ServiceExtensionAbility, and DataShareExtensionAbility run in another independent process. For details, see [Process Model (Stage Model)](process-model-stage.md).
> >
> For example, an application has one UIAbility component, one ServiceExtensionAbility, one DataShareExtensionAbility, two FormExtensionAbility, and one ImeExtensionAbility. When the application is running, there are three processes: > For example, an application has one UIAbility component, one ServiceExtensionAbility, one DataShareExtensionAbility, two FormExtensionAbility, and one ImeExtensionAbility. When the application is running, there are three processes:
> >
> - UIAbility, ServiceExtensionAbility, and DataShareExtensionAbility run in an independent process. > - UIAbility, ServiceExtensionAbility, and DataShareExtensionAbility run in an independent process.
> >
> - The two FormExtensionAbility components run in an independent process. > - The two FormExtensionAbility components run in an independent process.
> >
> - The two ImeExtensionAbility components run in an independent process. > - The two ImeExtensionAbility components run in an independent process.
<!--no_check-->
\ No newline at end of file
...@@ -3,12 +3,13 @@ ...@@ -3,12 +3,13 @@
During application development based on the Feature Ability (FA) model, the following tasks are involved in the application model. During application development based on the Feature Ability (FA) model, the following tasks are involved in the application model.
**Table 1** FA model development process
**Table 1** FA model development process
| Task| Introduction| Guide| | Task| Introduction| Guide|
| -------- | -------- | -------- | | -------- | -------- | -------- |
| Application component development| Use the PageAbility, ServiceAbility, DataAbility, and widgets of the FA model to develop applications.| - [Application- or Component-Level Configuration](application-component-configuration-fa.md)<br>- [PageAbility Component](pageability-overview.md)<br>- [ServiceAbility Component](serviceability-overview.md)<br>- [DataAbility Component](dataability-overview.md)<br>- [Widget Development](Widget-development-fa.md)<br>- [Context](application-context-fa.md)<br>- [Want](want-fa.md) | | Application component development| Use the PageAbility, ServiceAbility, DataAbility, and widgets of the FA model to develop applications.| - [Application- or Component-Level Configuration](application-component-configuration-fa.md)<br>- [PageAbility Component](pageability-overview.md)<br>- [ServiceAbility Component](serviceability-overview.md)<br>- [DataAbility Component](dataability-overview.md)<br>- [Widget Development](widget-development-fa.md)<br>- [Context](application-context-fa.md)<br>- [Want](want-fa.md)|
| Inter-process communication (IPC)| Learn the process model and common IPC modes of the FA model.| [Common Events](common-event-fa.md)<br>[Background Services](rpc.md) | | Process model| Learn the process model and common IPC modes of the FA model.| [Common Events](common-event-fa.md)<br>[Background Services](rpc.md)|
| Inter-thread communication| Learn the thread model and common inter-thread communication modes of the FA model.| [Inter-Thread Communication](itc-fa-overview.md)| | Thread model| Learn the thread model and common inter-thread communication modes of the FA model.| [Inter-Thread Communication](itc-fa-overview.md)|
| Mission management| Learn the basic concepts and typical scenarios of mission management in the FA model.| [Mission Management](mission-management-fa.md)| | Mission management| Learn the basic concepts and typical scenarios of mission management in the FA model.| [Mission Management](mission-management-fa.md)|
| Application configuration file| Learn the requirements for developing application configuration files in the FA model.| [Application Configuration File](../quick-start/application-configuration-file-overview-fa.md) | | Application configuration file| Learn the requirements for developing application configuration files in the FA model.| [Application Configuration File](../quick-start/application-configuration-file-overview-fa.md)|
...@@ -47,67 +47,42 @@ The table below describes the main APIs used for cross-device migration. For det ...@@ -47,67 +47,42 @@ The table below describes the main APIs used for cross-device migration. For det
## How to Develop ## How to Develop
1. Configure the data synchronization permission in the **module.json5** file. The sample code is as follows: 1. Request the **ohos.permission.DISTRIBUTED_DATASYNC** permission. For details, see [Declaring Permissions in the Configuration File](../security/accesstoken-guidelines.md#declaring-permissions-in-the-configuration-file).
2. Display a dialog box to ask authorization from the user when the application is started for the first time. For details, see [Requesting User Authorization](../security/accesstoken-guidelines.md#requesting-user-authorization).
3. Configure the fields related to cross-device migration in the configuration file.
Configure the application to support migration.
Set the **continuable** field in the **module.json5** file to **true**. The default value is **false**. If this parameter is set to **false**, the application cannot be continued on the target device.
```json ```json
{ {
"module": { "module": {
"requestPermissions":[ ...
{ "abilities": [
"name" : "ohos.permission.DISTRIBUTED_DATASYNC", {
...
"continuable": true,
} }
] ]
} }
} }
``` ```
2. Configure the fields related to cross-device migration in the configuration file. Configure the application launch type. For details, see [UIAbility Component Launch Type](uiability-launch-type.md).
- Configure the application to support migration.
Set the **continuable** field in the **module.json5** file to **true**. The default value is **false**. If this parameter is set to **false**, the application cannot be continued on the target device.
```json
{
"module": {
// ...
"abilities": [
{
// ...
"continuable": true,
}
]
}
}
```
- Configure the application launch type. For details, see [UIAbility Component Launch Type](uiability-launch-type.md).
3. Request the data synchronization permission. The sample code for displaying a dialog box to request the permission is as follows:
```ts
requestPermission() {
let context = this.context
let permissions: Array<string> = ['ohos.permission.DISTRIBUTED_DATASYNC']
context.requestPermissionsFromUser(permissions).then((data) => {
console.info("Succeed to request permission from user with data: "+ JSON.stringify(data))
}).catch((error) => {
console.info("Failed to request permission from user with error: "+ JSON.stringify(error))
})
}
```
4. Implement [onContinue()](../reference/apis/js-apis-app-ability-uiAbility.md#abilityoncontinue) in the UIAbility of the initiator. 4. Implement [onContinue()](../reference/apis/js-apis-app-ability-uiAbility.md#abilityoncontinue) in the UIAbility of the initiator.
[onContinue()](../reference/apis/js-apis-app-ability-uiAbility.md#abilityoncontinue) is called on the initiator. You can save the data in this method to implement application compatibility check and migration decision. [onContinue()](../reference/apis/js-apis-app-ability-uiAbility.md#abilityoncontinue) is called on the initiator. You can save the data in this method to implement application compatibility check and migration decision.
- Saving migrated data: You can save the data to be migrated in key-value pairs in **wantParam**. - Saving migrated data: You can save the data to be migrated in key-value pairs in **wantParam**.
- Checking application compatibility: You can obtain the version number of the target application from **wantParam** and check the compatibility between the target application and the current application. - Checking application compatibility: You can obtain the version number of the target application from **wantParam** and check the compatibility between the target application and the current application.
- Making a migration decision: You can determine whether to support the migration based on the return value of **onContinue()**. For details about the return value, see [Available APIs](#available-apis). - Making a migration decision: You can determine whether to support the migration based on the return value of **onContinue()**. For details about the return value, see [Available APIs](#available-apis).
The sample code is as follows: The sample code is as follows:
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility'; import UIAbility from '@ohos.app.ability.UIAbility';
import AbilityConstant from '@ohos.app.ability.AbilityConstant'; import AbilityConstant from '@ohos.app.ability.AbilityConstant';
......
# Using Emitter for Inter-Thread Communication # Using Emitter for Inter-Thread Communication
[Emitter](../reference/apis/js-apis-emitter.md) provides APIs for sending and processing events between threads, including the APIs for processing events that are subscribed to in persistent or one-shot manner, unsubscribing from events, and emitting events to the event queue. [Emitter](../reference/apis/js-apis-emitter.md) provides APIs for sending and processing events between threads, including the APIs for processing events that are subscribed to in persistent or one-shot manner, unsubscribing from events, and emitting events to the event queue.
...@@ -13,12 +14,12 @@ To develop the Emitter mode, perform the following steps: ...@@ -13,12 +14,12 @@ To develop the Emitter mode, perform the following steps:
// Define an event with eventId 1. // Define an event with eventId 1.
let event = { let event = {
eventId: 1 eventId: 1
}; };
// Trigger the callback after the event with eventId 1 is received. // Trigger the callback after the event with eventId 1 is received.
let callback = (eventData) => { let callback = (eventData) => {
console.info('event callback'); console.info('event callback');
}; };
// Subscribe to the event with eventId 1. // Subscribe to the event with eventId 1.
...@@ -29,21 +30,21 @@ To develop the Emitter mode, perform the following steps: ...@@ -29,21 +30,21 @@ To develop the Emitter mode, perform the following steps:
```ts ```ts
import emitter from "@ohos.events.emitter"; import emitter from "@ohos.events.emitter";
// Define an event with eventId 1 and priority Low. // Define an event with eventId 1 and priority Low.
let event = { let event = {
eventId: 1, eventId: 1,
priority: emitter.EventPriority.LOW priority: emitter.EventPriority.LOW
}; };
let eventData = { let eventData = {
data: { data: {
"content": "c", "content": "c",
"id": 1, "id": 1,
"isEmpty": false, "isEmpty": false,
} }
}; };
// Emit the event with eventId 1 and event content eventData. // Emit the event with eventId 1 and event content eventData.
emitter.emit(event, eventData); emitter.emit(event, eventData);
``` ```
# Using Worker for Inter-Thread Communication # Using Worker for Inter-Thread Communication
[Worker](../reference/apis/js-apis-worker.md) is an independent thread running in parallel with the main thread. The thread that creates the worker thread is referred to as the host thread. The script file passed in during worker creation is executed in the worker thread. Generally, time-consuming operations are processed in the worker thread. However, pages cannot be directly updated in the worker thread. [Worker](../reference/apis/js-apis-worker.md) is an independent thread running in parallel with the main thread. The thread that creates the worker thread is referred to as the host thread. The script file passed in during worker creation is executed in the worker thread. Generally, time-consuming operations are processed in the worker thread. However, pages cannot be directly updated in the worker thread.
...@@ -9,13 +10,13 @@ To develop the Worker mode, perform the following steps: ...@@ -9,13 +10,13 @@ To develop the Worker mode, perform the following steps:
1. Configure the **buildOption** field in the [module-level build-profile.json5](https://developer.harmonyos.com/en/docs/documentation/doc-guides/ohos-building-configuration-0000001218440654#section6887184182020) file of the project. 1. Configure the **buildOption** field in the [module-level build-profile.json5](https://developer.harmonyos.com/en/docs/documentation/doc-guides/ohos-building-configuration-0000001218440654#section6887184182020) file of the project.
```ts ```ts
"buildOption": { "buildOption": {
"sourceOption": { "sourceOption": {
"workers": [ "workers": [
"./src/main/ets/workers/worker.ts" "./src/main/ets/workers/worker.ts"
] ]
}
} }
}
``` ```
2. Create the **worker.ts** file based on the configuration in **build-profile.json5**. 2. Create the **worker.ts** file based on the configuration in **build-profile.json5**.
...@@ -27,9 +28,9 @@ To develop the Worker mode, perform the following steps: ...@@ -27,9 +28,9 @@ To develop the Worker mode, perform the following steps:
// Process messages from the main thread. // Process messages from the main thread.
parent.onmessage = function(message) { parent.onmessage = function(message) {
console.info("onmessage: " + message) console.info("onmessage: " + message)
// Send a message to the main thread. // Send a message to the main thread.
parent.postMessage("message from worker thread.") parent.postMessage("message from worker thread.")
} }
``` ```
...@@ -46,10 +47,10 @@ To develop the Worker mode, perform the following steps: ...@@ -46,10 +47,10 @@ To develop the Worker mode, perform the following steps:
// Process messages from the worker thread. // Process messages from the worker thread.
wk.onmessage = function(message) { wk.onmessage = function(message) {
console.info("message from worker: " + message) console.info("message from worker: " + message)
// Stop the worker thread based on service requirements. // Stop the worker thread based on service requirements.
wk.terminate() wk.terminate();
} }
``` ```
...@@ -57,23 +58,22 @@ To develop the Worker mode, perform the following steps: ...@@ -57,23 +58,22 @@ To develop the Worker mode, perform the following steps:
```ts ```ts
import worker from '@ohos.worker'; import worker from '@ohos.worker';
let wk = new worker.ThreadWorker("../workers/worker.ts"); let wk = new worker.ThreadWorker("../workers/worker.ts");
// Send a message to the worker thread. // Send a message to the worker thread.
wk.postMessage("message from main thread.") wk.postMessage("message from main thread.")
// Process messages from the worker thread. // Process messages from the worker thread.
wk.onmessage = function(message) { wk.onmessage = function(message) {
console.info("message from worker: " + message) console.info("message from worker: " + message)
// Stop the worker thread based on service requirements. // Stop the worker thread based on service requirements.
wk.terminate() wk.terminate();
} }
``` ```
> **NOTE** > **NOTE**
> >
> - If the relative path of **worker.ts** configured in **build-profile.json5** is **./src/main/ets/workers/worker.ts**, pass in the path **entry/ets/workers/worker.ts** when creating a worker thread in the stage model, and pass in the path **../workers/worker.ts** when creating a worker thread in the FA model. > - If the relative path of **worker.ts** configured in **build-profile.json5** is **./src/main/ets/workers/worker.ts**, pass in the path **entry/ets/workers/worker.ts** when creating a worker thread in the stage model, and pass in the path **../workers/worker.ts** when creating a worker thread in the FA model.
>
> - For details about the data types supported between the main thread and worker thread, see [Sequenceable Data Types](../reference/apis/js-apis-worker.md#sequenceable-data-types). > - For details about the data types supported between the main thread and worker thread, see [Sequenceable Data Types](../reference/apis/js-apis-worker.md#sequenceable-data-types).
...@@ -5,7 +5,6 @@ Setting a unique icon and name for each mission snapshot of an application helps ...@@ -5,7 +5,6 @@ Setting a unique icon and name for each mission snapshot of an application helps
By default, the **icon** and **label** fields in the [abilities tag](../quick-start/module-configuration-file.md#abilities) of the [module.json5 file](../quick-start/module-configuration-file.md) are used to set the icon and label. By default, the **icon** and **label** fields in the [abilities tag](../quick-start/module-configuration-file.md#abilities) of the [module.json5 file](../quick-start/module-configuration-file.md) are used to set the icon and label.
Figure 1 Mission snapshot of a UIAbility Figure 1 Mission snapshot of a UIAbility
![](figures/mission-list-recent.png) ![](figures/mission-list-recent.png)
You can also use [UIAbilityContext.setMissionIcon()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextsetmissionicon) and [UIAbilityContext.setMissionLabel()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextsetmissionlabel) to customize the icon and name for a mission snapshot. For example, for a UIAbility instance in multiton mode, you can configure the icon and name for each mission snapshot based on different functions. You can also use [UIAbilityContext.setMissionIcon()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextsetmissionicon) and [UIAbilityContext.setMissionLabel()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextsetmissionlabel) to customize the icon and name for a mission snapshot. For example, for a UIAbility instance in multiton mode, you can configure the icon and name for each mission snapshot based on different functions.
...@@ -21,15 +20,16 @@ Call [UIAbilityContext.setMissionIcon()](../reference/apis/js-apis-inner-applica ...@@ -21,15 +20,16 @@ Call [UIAbilityContext.setMissionIcon()](../reference/apis/js-apis-inner-applica
```ts ```ts
let imagePixelMap: PixelMap = undefined; // Obtain the PixelMap information. let imagePixelMap: PixelMap = undefined; // Obtain the PixelMap information.
this.context.setMissionIcon(imagePixelMap, (err) => { context.setMissionIcon(imagePixelMap, (err) => {
console.error(`setMissionLabel failed, code is ${err.code}, message is ${err.message}`); if (err.code) {
console.error(`Failed to set mission icon. Code is ${err.code}, message is ${err.message}`);
}
}) })
``` ```
The display effect is shown below. The display effect is shown below.
Figure 2 Mission snapshot icon Figure 2 Mission snapshot icon
![](figures/mission-set-task-snapshot-icon.png) ![](figures/mission-set-task-snapshot-icon.png)
## Setting a Mission Snapshot Name ## Setting a Mission Snapshot Name
...@@ -38,14 +38,13 @@ Call [UIAbilityContext.setMissionLabel()](../reference/apis/js-apis-inner-applic ...@@ -38,14 +38,13 @@ Call [UIAbilityContext.setMissionLabel()](../reference/apis/js-apis-inner-applic
```ts ```ts
this.context.setMissionLabel('test').then(() => { this.context.setMissionLabel('test').then(() => {
console.info('setMissionLabel succeeded.'); console.info('Succeeded in seting mission label.');
}).catch((err) => { }).catch((err) => {
console.error(`setMissionLabel failed, code is ${err.code}, message is ${err.message}`); console.error(`Failed to set mission label. Code is ${err.code}, message is ${err.message}`);
}); });
``` ```
The display effect is shown below. The display effect is shown below.
Figure 3 Mission snapshot name Figure 3 Mission snapshot name
![](figures/mission-set-task-snapshot-label.png) ![](figures/mission-set-task-snapshot-label.png)
...@@ -3,7 +3,7 @@ ...@@ -3,7 +3,7 @@
When switching an application from the FA model to the stage model, you must migrate the configurations under the **module** tag in the **config.json** file to the **module** tag in the **module.json5** file. When switching an application from the FA model to the stage model, you must migrate the configurations under the **module** tag in the **config.json** file to the **module** tag in the **module.json5** file.
### Table 1 module Comparison **Table 1** module comparison
| Field Name in the FA Model| Field Description| Field Name in the Stage Model| Difference| | Field Name in the FA Model| Field Description| Field Name in the Stage Model| Difference|
| -------- | -------- | -------- | -------- | | -------- | -------- | -------- | -------- |
...@@ -15,8 +15,8 @@ When switching an application from the FA model to the stage model, you must mig ...@@ -15,8 +15,8 @@ When switching an application from the FA model to the stage model, you must mig
| moduleType in the distro object| Type of the HAP file. The value can be **entry** or **feature**. For the HAR type, set this field to **har**.| type | The field name is changed.| | moduleType in the distro object| Type of the HAP file. The value can be **entry** or **feature**. For the HAR type, set this field to **har**.| type | The field name is changed.|
| installationFree in the distro object| Whether the HAP file supports the installation-free feature.| installationFree | The field name is changed.| | installationFree in the distro object| Whether the HAP file supports the installation-free feature.| installationFree | The field name is changed.|
| deliveryWithInstall in the distro object| Whether the HAP file is installed with the application.| deliveryWithInstall | The field name is changed.| | deliveryWithInstall in the distro object| Whether the HAP file is installed with the application.| deliveryWithInstall | The field name is changed.|
| metaData | Metadata of the HAP file.| metadata | See [Table 2](#table-2-metadata-comparison).| | metaData | Metadata of the HAP file.| metadata | For details, see Table 2.|
| abilities | All abilities in the current module.| abilities | See [Table 5](#table-5-abilities-comparison).| | abilities | All abilities in the current module.| abilities | For details, see Table 5.|
| js | A set of JS modules developed using ArkUI. Each element in the set represents the information about a JS module.| pages | The stage model retains **pages** under the **module** tag. The window configuration is the lower level of **pages**.| | js | A set of JS modules developed using ArkUI. Each element in the set represents the information about a JS module.| pages | The stage model retains **pages** under the **module** tag. The window configuration is the lower level of **pages**.|
| shortcuts | Shortcuts of the application.| shortcut_config.json| In the stage model, the **shortcut_config.json** file is defined in **resources/base/profile** in the development view.| | shortcuts | Shortcuts of the application.| shortcut_config.json| In the stage model, the **shortcut_config.json** file is defined in **resources/base/profile** in the development view.|
| reqPermissions | Permissions that the application requests from the system when it is running.| requestPermissions | The field name is changed.| | reqPermissions | Permissions that the application requests from the system when it is running.| requestPermissions | The field name is changed.|
...@@ -27,38 +27,38 @@ When switching an application from the FA model to the stage model, you must mig ...@@ -27,38 +27,38 @@ When switching an application from the FA model to the stage model, you must mig
| entryTheme | Keyword of an OpenHarmony internal theme.| / | This configuration is not supported in the stage model.| | entryTheme | Keyword of an OpenHarmony internal theme.| / | This configuration is not supported in the stage model.|
### Table 2 metaData Comparison **Table 2** metaData comparison
| Field Name Under metaData in the FA Model| Field Description| Field Name Under metaData in the Stage Model| Difference| | Field Name in the FA Model| Field Description| Field Name in the Stage Model| Difference|
| -------- | -------- | -------- | -------- | | -------- | -------- | -------- | -------- |
| parameters | Metadata of the parameters to be passed for calling the ability.| / | This configuration is not supported in the stage model.| | parameters | Metadata of the parameters to be passed for calling the ability.| / | This configuration is not supported in the stage model.|
| results | Metadata of the ability return value.| / | This configuration is not supported in the stage model.| | results | Metadata of the ability return value.| / | This configuration is not supported in the stage model.|
| customizeData | Custom metadata of the parent component. **parameters** and **results** cannot be configured in **application**.| metadata | See [Table 3](#table-3-comparison-between-customizedata-under-metadata-in-the-fa-model-and-metadata-in-the-stage-model).| | customizeData | Custom metadata of the parent component. **parameters** and **results** cannot be configured in **application**.| metadata | **For details**, see Table 3.|
### Table 3 Comparison Between customizeData Under metaData in the FA Model and metadata in the Stage Model **Table 3** Comparison between customizeData under metaData in the FA model and metadata in the stage Model
| Field Name Under customizeData in metaData in the FA Model| Field Description| Field Name Under metaData in the Stage Model| Difference| | Field Name in the FA Model| Field Description| Field Name in the Stage Model| Difference|
| -------- | -------- | -------- | -------- | | -------- | -------- | -------- | -------- |
| name | Key name that identifies a data item. The value is a string with a maximum of 255 bytes.| name | None.| | name | Key name that identifies a data item. The value is a string with a maximum of 255 bytes.| name | None.|
| value | Value of the data item. The value is a string with a maximum of 255 bytes.| value | None.| | value | Value of the data item. The value is a string with a maximum of 255 bytes.| value | None.|
| extra | Format of the current custom data. The value is the resource value of **extra**.| resource | The field name is changed. For details, see [Table 4](#table 4-metadata-examples).| | extra | Format of the current custom data. The value is the resource value of **extra**.| resource | The field name is changed. For details, see Table 4.|
### Table 4 metaData Examples **Table 4** metaData examples
| Example in the FA Model| Example in the Stage Model| | Example in the FA Model| Example in the Stage Model|
| -------- | -------- | | -------- | -------- |
| "meteData": {<br> "customizeDate": [{<br> "name": "label",<br> "value": "string",<br> "extra": "$string:label",<br> }]<br>} | "meteData": [{<br> "name": "label",<br> "value": "string",<br> "resource": "$string:label",<br>}] | | "meteData": {<br> "customizeDate": [{<br> "name": "label",<br> "value": "string",<br> "extra": "$string:label",<br> }]<br>} | "meteData": [{<br> "name": "label",<br> "value": "string",<br> "resource": "$string:label",<br>}] |
### Table 5 abilities Comparison **Table 5** abilities comparison
| Field Name Under abilities in the FA Model| Field Description| Field Name Under abilities in the Stage Model| Difference| | Field Name Under abilities in the FA Model| Field Description| Field Name Under abilities in the Stage Model| Difference|
| -------- | -------- | -------- | -------- | | -------- | -------- | -------- | -------- |
| process | Name of the process running the application or ability.| / | The stage model does not support configuration of **process** under **abilities**. The configuration of **process** is available under the **module** tag.| | process | Name of the process running the application or ability.| / | The stage model does not support configuration of **process** under **abilities**. The configuration of **process** is available under the **module** tag.|
| uri | URI of the ability.| / | This configuration is not supported in the stage model.| | uri | URI of the ability.| / | This configuration is not supported in the stage model.|
| deviceCapability | Device capabilities required to run the ability.| / | This configuration is not supported in the stage model.| | deviceCapability | Device capabilities required to run the ability.| / | This configuration is not supported in the stage model.|
| metaData | Metadata of the ability.| metadata | See [Table 2](#table-2-metadata-comparison).| | metaData | Metadata of the ability.| metadata | For details, see Table 2.|
| type | Ability type.| / | This configuration is not supported in the stage model.| | type | Ability type.| / | This configuration is not supported in the stage model.|
| grantPermission | Whether permissions can be granted for any data in the ability.| / | The stage model does not support such a configuration under **abilities**.| | grantPermission | Whether permissions can be granted for any data in the ability.| / | The stage model does not support such a configuration under **abilities**.|
| readPermission | Permission required for reading data in the ability. This field applies only to the ability using the Data template.| / | In the stage model, this configuration is available under **extensionAbilities**, but not **abilities**.| | readPermission | Permission required for reading data in the ability. This field applies only to the ability using the Data template.| / | In the stage model, this configuration is available under **extensionAbilities**, but not **abilities**.|
...@@ -71,5 +71,5 @@ When switching an application from the FA model to the stage model, you must mig ...@@ -71,5 +71,5 @@ When switching an application from the FA model to the stage model, you must mig
| formsEnabled | Whether the ability can provide widgets.| / | This configuration is not supported in the stage model.| | formsEnabled | Whether the ability can provide widgets.| / | This configuration is not supported in the stage model.|
| forms | Information about the widgets used by the ability. This field is valid only when **formsEnabled** is set to **true**.| form_config.json| In the stage model, the **form_config.json** file is defined in **resources/base/profile** in the development view.| | forms | Information about the widgets used by the ability. This field is valid only when **formsEnabled** is set to **true**.| form_config.json| In the stage model, the **form_config.json** file is defined in **resources/base/profile** in the development view.|
| srcLanguage | Programming language used to develop the ability.| / | This configuration is not supported in the stage model.| | srcLanguage | Programming language used to develop the ability.| / | This configuration is not supported in the stage model.|
| srcPath | Path of the JS component code corresponding to the ability.| srcEnty | Path of the JS code corresponding to the ability.| | srcPath | Path of the JS component code corresponding to the ability.| srcEntry | Path of the JS code corresponding to the ability.|
| uriPermission | Application data that the ability can access.| / | This configuration is not supported in the stage model.| | uriPermission | Application data that the ability can access.| / | This configuration is not supported in the stage model.|
...@@ -5,7 +5,8 @@ ...@@ -5,7 +5,8 @@
A single UIAbility component can implement multiple pages and redirection between these pages. The redirection relationship inside the UIAbility component is called page stack, which is managed by the ArkUI framework. For example, Page1 -&gt; Page2 -&gt; Page3 of UIAbility1 and PageA -&gt; PageB -&gt; PageC of UIAbility2 in the figure below are two page stacks. A single UIAbility component can implement multiple pages and redirection between these pages. The redirection relationship inside the UIAbility component is called page stack, which is managed by the ArkUI framework. For example, Page1 -&gt; Page2 -&gt; Page3 of UIAbility1 and PageA -&gt; PageB -&gt; PageC of UIAbility2 in the figure below are two page stacks.
**Figure 1** Page stack **Figure 1** Page stack
![mission-record](figures/mission-record.png) ![mission-record](figures/mission-record.png)
- A page stack is formed as follows (Steps 2, 3, 5, and 6 are page redirection and managed by ArkUI): - A page stack is formed as follows (Steps 2, 3, 5, and 6 are page redirection and managed by ArkUI):
......
...@@ -5,7 +5,7 @@ Depending on the launch type, the action performed when the PageAbility starts d ...@@ -5,7 +5,7 @@ Depending on the launch type, the action performed when the PageAbility starts d
**Table 1** PageAbility launch types **Table 1** PageAbility launch types
| Launch Type| Meaning | Description| | Launch Type| Meaning| Description |
| -------- | -------- | -------- | | -------- | -------- | -------- |
| singleton | Singleton mode| Each time **startAbility()** is called, if an ability instance of this type already exists in the application process, the instance is reused. There is only one ability instance of this type in **Recents**.<br>A typical scenario is as follows: When a user opens a video playback application and watches a video, returns to the home screen, and opens the video playback application again, the video that the user watched before returning to the home screen is still played.| | singleton | Singleton mode| Each time **startAbility()** is called, if an ability instance of this type already exists in the application process, the instance is reused. There is only one ability instance of this type in **Recents**.<br>A typical scenario is as follows: When a user opens a video playback application and watches a video, returns to the home screen, and opens the video playback application again, the video that the user watched before returning to the home screen is still played.|
| standard | Multiton mode| Default type. Each time **startAbility()** is called, a new ability instance is created in the application process. Multiple ability instances of this type are displayed in **Recents**.<br>A typical scenario is as follows: When a user opens a document application and touches **New**, a new document task is created. Multiple new document missions are displayed in **Recents**.| | standard | Multiton mode| Default type. Each time **startAbility()** is called, a new ability instance is created in the application process. Multiple ability instances of this type are displayed in **Recents**.<br>A typical scenario is as follows: When a user opens a document application and touches **New**, a new document task is created. Multiple new document missions are displayed in **Recents**.|
...@@ -16,13 +16,13 @@ You can set **launchType** in the **config.json** file to configure the launch t ...@@ -16,13 +16,13 @@ You can set **launchType** in the **config.json** file to configure the launch t
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
// singleton means the singleton mode. // singleton means the singleton mode.
// standard means the multiton mode. // standard means the multiton mode.
"launchType": "standard", "launchType": "standard",
// ... ...
} }
] ]
} }
...@@ -32,7 +32,6 @@ You can set **launchType** in the **config.json** file to configure the launch t ...@@ -32,7 +32,6 @@ You can set **launchType** in the **config.json** file to configure the launch t
When the PageAbility is started in multiton mode or it is started in singleton mode for the first time, the [PageAbility lifecycle callbacks](pageability-lifecycle.md#table13118194914476) are triggered. When it is not started for the first time in singleton mode, the **onNewWant()** callback (as described in the table below) is triggered, but the **onCreate()** callback is not. When the PageAbility is started in multiton mode or it is started in singleton mode for the first time, the [PageAbility lifecycle callbacks](pageability-lifecycle.md#table13118194914476) are triggered. When it is not started for the first time in singleton mode, the **onNewWant()** callback (as described in the table below) is triggered, but the **onCreate()** callback is not.
**Table 2** Callbacks specific to the singleton mode **Table 2** Callbacks specific to the singleton mode
| API| Description| | API| Description|
......
...@@ -7,14 +7,13 @@ Generally, UI redirection within an application is triggered by users. However, ...@@ -7,14 +7,13 @@ Generally, UI redirection within an application is triggered by users. However,
The PageAbility has a UI. It can use **startAbility()** to start an ability that has a UI and is visible to users. The PageAbility has a UI. It can use **startAbility()** to start an ability that has a UI and is visible to users.
The **exported** field under **abilities** in the **config.json** file specifies whether an ability can be started by other application components. The **visible** field under **abilities** in the **config.json** file specifies whether an ability can be started by other application components.
**Table 1** Description of visible
**Table 1** Description of exported
| Name| Description| Initial Value Allowed| | Name| Description| Initial Value Allowed|
| -------- | -------- | -------- | | -------- | -------- | -------- |
| exported | Whether the ability can be called by other applications.<br>**true**: The ability can be called by any application.<br>**false**: The ability can be called only by other components of the same application.| Yes (initial value: **false**)| | visible | Whether the ability can be called by other applications.<br>**true**: The ability can be called by any application.<br>**false**: The ability can be called only by other components of the same application.| Yes (initial value: **false**)|
To enable an ability to be called by any application, configure the **config.json** file as follows: To enable an ability to be called by any application, configure the **config.json** file as follows:
...@@ -22,11 +21,11 @@ To enable an ability to be called by any application, configure the **config.jso ...@@ -22,11 +21,11 @@ To enable an ability to be called by any application, configure the **config.jso
```ts ```ts
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
"exported": "true", "visible": "true",
// ... ...
} }
] ]
} }
...@@ -34,4 +33,4 @@ To enable an ability to be called by any application, configure the **config.jso ...@@ -34,4 +33,4 @@ To enable an ability to be called by any application, configure the **config.jso
``` ```
If the ability contains **skills**, you are advised to set **exported** to **true** so that the ability can be [implicitly started](explicit-implicit-want-mappings.md#matching-rules-of-implicit-want) by other applications. If this attribute is set to **false**, the system returns **PERMISSION_DENIED** when other applications attempt to start the ability. In this case, a system application can request the [START_INVISIBLE_ABILITY](../security/permission-list.md) permission to start the ability. Example abilities with **exported** set to **false** are home screen, voice assistant, or search assistant. If the ability contains **skills**, you are advised to set **visible** to **true** so that the ability can be [implicitly started](explicit-implicit-want-mappings.md) by other applications. If this attribute is set to **false**, the system returns **PERMISSION_DENIED** when other applications attempt to start the ability. In this case, a system application can request the [START_INVISIBLE_ABILITY](../security/permission-list.md) permission to start the ability. Example abilities with **visible** set to **false** are home screen, voice assistant, or search assistant.
...@@ -9,37 +9,7 @@ During application development, you must declare the required permission in the ...@@ -9,37 +9,7 @@ During application development, you must declare the required permission in the
To declare a permission in **config.json**, add **reqPermissions** under **module** and list the permission. To declare a permission in **config.json**, add **reqPermissions** under **module** and list the permission.
For example, to request the permission to access the calendar, perform the following steps:
For example, to declare the permission to access the calendar, request the **ohos.permission.READ_CALENDAR** permission. For details, see [Permission Application Guide](../security/accesstoken-guidelines.md#declaring-permissions-in-the-configuration-file). 1. Request the **ohos.permission.DISTRIBUTED_DATASYNC** permission. For details, see [Declaring Permissions in the Configuration File](../security/accesstoken-guidelines.md#declaring-permissions-in-the-configuration-file).
2. Display a dialog box to ask authorization from the user when the application is started for the first time. For details, see [Requesting User Authorization](../security/accesstoken-guidelines.md#requesting-user-authorization).
The sample code in the **config.json** file is as follows:
```json
{
"module": {
// ...
"reqPermissions": [
{
"name": "ohos.permission.READ_CALENDAR"
// ...
}
]
}
}
```
Request the permission from uses in the form of a dialog box:
```ts
import featureAbility from '@ohos.ability.featureAbility';
let context = featureAbility.getContext();
let permissions: Array<string> = ['ohos.permission.READ_CALENDAR']
context.requestPermissionsFromUser(permissions, 1).then((data) => {
console.info("Succeed to request permission from user with data: " + JSON.stringify(data))
}).catch((error) => {
console.info("Failed to request permission from user with error: " + JSON.stringify(error))
})
```
...@@ -29,6 +29,7 @@ Note the following: ...@@ -29,6 +29,7 @@ Note the following:
[ServiceExtensionAbility](../reference/apis/js-apis-app-ability-serviceExtensionAbility.md) provides the callbacks **onCreate()**, **onRequest()**, **onConnect()**, **onDisconnect()**, and **onDestory()**. Override them as required. The following figure shows the lifecycle of ServiceExtensionAbility. [ServiceExtensionAbility](../reference/apis/js-apis-app-ability-serviceExtensionAbility.md) provides the callbacks **onCreate()**, **onRequest()**, **onConnect()**, **onDisconnect()**, and **onDestory()**. Override them as required. The following figure shows the lifecycle of ServiceExtensionAbility.
**Figure 1** ServiceExtensionAbility lifecycle **Figure 1** ServiceExtensionAbility lifecycle
![ServiceExtensionAbility-lifecycle](figures/ServiceExtensionAbility-lifecycle.png) ![ServiceExtensionAbility-lifecycle](figures/ServiceExtensionAbility-lifecycle.png)
- **onCreate** - **onCreate**
...@@ -109,7 +110,7 @@ export default class ServiceExtImpl extends IdlServiceExtStub { ...@@ -109,7 +110,7 @@ export default class ServiceExtImpl extends IdlServiceExtStub {
insertDataToMap(key: string, val: number, callback: insertDataToMapCallback): void { insertDataToMap(key: string, val: number, callback: insertDataToMapCallback): void {
// Implement service logic. // Implement service logic.
console.log(TAG, `insertDataToMap, key: ${key} val: ${val}`); console.info(TAG, `insertDataToMap, key: ${key} val: ${val}`);
callback(ERR_OK); callback(ERR_OK);
} }
} }
...@@ -175,7 +176,7 @@ To manually create a ServiceExtensionAbility in the DevEco Studio project, perfo ...@@ -175,7 +176,7 @@ To manually create a ServiceExtensionAbility in the DevEco Studio project, perfo
```json ```json
{ {
"module": { "module": {
// ... ...
"extensionAbilities": [ "extensionAbilities": [
{ {
"name": "ServiceExtAbility", "name": "ServiceExtAbility",
...@@ -201,41 +202,43 @@ A system application uses the [startServiceExtensionAbility()](../reference/apis ...@@ -201,41 +202,43 @@ A system application uses the [startServiceExtensionAbility()](../reference/apis
1. Start a new ServiceExtensionAbility in a system application. For details about how to obtain the context, see [Obtaining the Context of UIAbility](uiability-usage.md#obtaining-the-context-of-uiability). 1. Start a new ServiceExtensionAbility in a system application. For details about how to obtain the context, see [Obtaining the Context of UIAbility](uiability-usage.md#obtaining-the-context-of-uiability).
```ts ```ts
let context = ...; // UIAbilityContext
let want = { let want = {
"deviceId": "", "deviceId": "",
"bundleName": "com.example.myapplication", "bundleName": "com.example.myapplication",
"abilityName": "ServiceExtAbility" "abilityName": "ServiceExtAbility"
}; };
this.context.startServiceExtensionAbility(want).then(() => { context.startServiceExtensionAbility(want).then(() => {
console.info('startServiceExtensionAbility success'); console.info('Succeeded in starting ServiceExtensionAbility.');
}).catch((error) => { }).catch((err) => {
console.info('startServiceExtensionAbility failed'); console.error(`Failed to start ServiceExtensionAbility. Code is ${err.code}, message is ${err.message}`);
}) })
``` ```
2. Stop ServiceExtensionAbility in the system application. 2. Stop ServiceExtensionAbility in the system application.
```ts ```ts
let context = ...; // UIAbilityContext
let want = { let want = {
"deviceId": "", "deviceId": "",
"bundleName": "com.example.myapplication", "bundleName": "com.example.myapplication",
"abilityName": "ServiceExtAbility" "abilityName": "ServiceExtAbility"
}; };
this.context.stopServiceExtensionAbility(want).then(() => { context.stopServiceExtensionAbility(want).then(() => {
console.info('stopServiceExtensionAbility success'); console.info('Succeeded in stoping ServiceExtensionAbility.');
}).catch((error) => { }).catch((err) => {
console.info('stopServiceExtensionAbility failed'); console.error(`Failed to stop ServiceExtensionAbility. Code is ${err.code}, message is ${err.message}`);
}) })
``` ```
3. ServiceExtensionAbility stops itself. 3. ServiceExtensionAbility stops itself.
```ts ```ts
// this is the current ServiceExtensionAbility component. let context = ...; // ServiceExtensionContext
this.context.terminateSelf().then(() => { context.terminateSelf().then(() => {
console.info('terminateSelf success'); console.info('Succeeded in terminating self.');
}).catch((error) => { }).catch((err) => {
console.info('terminateSelf failed'); console.error(`Failed to terminate self. Code is ${err.code}, message is ${err.message}`);
}) })
``` ```
...@@ -257,27 +260,27 @@ The ServiceExtensionAbility component returns an IRemoteObject in the **onConnec ...@@ -257,27 +260,27 @@ The ServiceExtensionAbility component returns an IRemoteObject in the **onConnec
```ts ```ts
let want = { let want = {
"deviceId": "", "deviceId": "",
"bundleName": "com.example.myapplication", "bundleName": "com.example.myapplication",
"abilityName": "ServiceExtAbility" "abilityName": "ServiceExtAbility"
}; };
let options = { let options = {
onConnect(elementName, remote) { onConnect(elementName, remote) {
/* The input parameter remote is the object returned by ServiceExtensionAbility in the onConnect lifecycle callback. /* The input parameter remote is the object returned by ServiceExtensionAbility in the onConnect lifecycle callback.
* This object is used for communication with ServiceExtensionAbility. For details, see the section below. * This object is used for communication with ServiceExtensionAbility. For details, see the section below.
*/ */
console.info('onConnect callback'); console.info('onConnect callback');
if (remote === null) { if (remote === null) {
console.info(`onConnect remote is null`); console.info(`onConnect remote is null`);
return; return;
}
},
onDisconnect(elementName) {
console.info('onDisconnect callback')
},
onFailed(code) {
console.info('onFailed callback')
} }
},
onDisconnect(elementName) {
console.info('onDisconnect callback')
},
onFailed(code) {
console.info('onFailed callback')
}
} }
// The ID returned after the connection is set up must be saved. The ID will be passed for service disconnection. // The ID returned after the connection is set up must be saved. The ID will be passed for service disconnection.
let connectionId = this.context.connectServiceExtensionAbility(want, options); let connectionId = this.context.connectServiceExtensionAbility(want, options);
...@@ -288,9 +291,9 @@ The ServiceExtensionAbility component returns an IRemoteObject in the **onConnec ...@@ -288,9 +291,9 @@ The ServiceExtensionAbility component returns an IRemoteObject in the **onConnec
```ts ```ts
// connectionId is returned when connectServiceExtensionAbility is called and needs to be manually maintained. // connectionId is returned when connectServiceExtensionAbility is called and needs to be manually maintained.
this.context.disconnectServiceExtensionAbility(connectionId).then((data) => { this.context.disconnectServiceExtensionAbility(connectionId).then((data) => {
console.info('disconnectServiceExtensionAbility success'); console.info('disconnectServiceExtensionAbility success');
}).catch((error) => { }).catch((error) => {
console.error('disconnectServiceExtensionAbility failed'); console.error('disconnectServiceExtensionAbility failed');
}) })
``` ```
...@@ -305,27 +308,27 @@ After obtaining the [rpc.RemoteObject](../reference/apis/js-apis-rpc.md#iremoteo ...@@ -305,27 +308,27 @@ After obtaining the [rpc.RemoteObject](../reference/apis/js-apis-rpc.md#iremoteo
import IdlServiceExtProxy from '../IdlServiceExt/idl_service_ext_proxy'; import IdlServiceExtProxy from '../IdlServiceExt/idl_service_ext_proxy';
let options = { let options = {
onConnect(elementName, remote) { onConnect(elementName, remote) {
console.info('onConnect callback'); console.info('onConnect callback');
if (remote === null) { if (remote === null) {
console.info(`onConnect remote is null`); console.info(`onConnect remote is null`);
return; return;
}
let serviceExtProxy = new IdlServiceExtProxy(remote);
// Communication is carried out by interface calling, without exposing RPC details.
serviceExtProxy.processData(1, (errorCode, retVal) => {
console.log(`processData, errorCode: ${errorCode}, retVal: ${retVal}`);
});
serviceExtProxy.insertDataToMap('theKey', 1, (errorCode) => {
console.log(`insertDataToMap, errorCode: ${errorCode}`);
})
},
onDisconnect(elementName) {
console.info('onDisconnect callback')
},
onFailed(code) {
console.info('onFailed callback')
} }
let serviceExtProxy = new IdlServiceExtProxy(remote);
// Communication is carried out by interface calling, without exposing RPC details.
serviceExtProxy.processData(1, (errorCode, retVal) => {
console.info(`processData, errorCode: ${errorCode}, retVal: ${retVal}`);
});
serviceExtProxy.insertDataToMap('theKey', 1, (errorCode) => {
console.info(`insertDataToMap, errorCode: ${errorCode}`);
})
},
onDisconnect(elementName) {
console.info('onDisconnect callback')
},
onFailed(code) {
console.info('onFailed callback')
}
} }
``` ```
...@@ -333,40 +336,40 @@ After obtaining the [rpc.RemoteObject](../reference/apis/js-apis-rpc.md#iremoteo ...@@ -333,40 +336,40 @@ After obtaining the [rpc.RemoteObject](../reference/apis/js-apis-rpc.md#iremoteo
```ts ```ts
import rpc from '@ohos.rpc'; import rpc from '@ohos.rpc';
const REQUEST_CODE = 1; const REQUEST_CODE = 1;
let options = { let options = {
onConnect(elementName, remote) { onConnect(elementName, remote) {
console.info('onConnect callback'); console.info('onConnect callback');
if (remote === null) { if (remote === null) {
console.info(`onConnect remote is null`); console.info(`onConnect remote is null`);
return; return;
}
// Directly call the RPC interface to send messages to the server. The client needs to serialize the input parameters and deserialize the return values. The process is complex.
let option = new rpc.MessageOption();
let data = new rpc.MessageSequence();
let reply = new rpc.MessageSequence();
data.writeInt(100);
// @param code Indicates the service request code sent by the client.
// @param data Indicates the {@link MessageSequence} object sent by the client.
// @param reply Indicates the response message object sent by the remote service.
// @param options Specifies whether the operation is synchronous or asynchronous.
//
// @return Returns {@code true} if the operation is successful; returns {@code false} otherwise.
remote.sendMessageRequest(REQUEST_CODE, data, reply, option).then((ret) => {
let msg = reply.readInt();
console.info(`sendMessageRequest ret:${ret} msg:${msg}`);
}).catch((error) => {
console.info('sendMessageRequest failed');
});
},
onDisconnect(elementName) {
console.info('onDisconnect callback')
},
onFailed(code) {
console.info('onFailed callback')
} }
// Directly call the RPC interface to send messages to the server. The client needs to serialize the input parameters and deserialize the return values. The process is complex.
let option = new rpc.MessageOption();
let data = new rpc.MessageSequence();
let reply = new rpc.MessageSequence();
data.writeInt(100);
// @param code Indicates the service request code sent by the client.
// @param data Indicates the {@link MessageSequence} object sent by the client.
// @param reply Indicates the response message object sent by the remote service.
// @param options Specifies whether the operation is synchronous or asynchronous.
//
// @return Returns {@code true} if the operation is successful; returns {@code false} otherwise.
remote.sendMessageRequest(REQUEST_CODE, data, reply, option).then((ret) => {
let msg = reply.readInt();
console.info(`sendMessageRequest ret:${ret} msg:${msg}`);
}).catch((error) => {
console.info('sendMessageRequest failed');
});
},
onDisconnect(elementName) {
console.info('onDisconnect callback')
},
onFailed(code) {
console.info('onFailed callback')
}
} }
``` ```
...@@ -381,8 +384,8 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i ...@@ -381,8 +384,8 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i
```ts ```ts
import rpc from '@ohos.rpc'; import rpc from '@ohos.rpc';
import bundleManager from '@ohos.bundle.bundleManager'; import bundleManager from '@ohos.bundle.bundleManager';
import {processDataCallback} from './i_idl_service_ext'; import { processDataCallback } from './i_idl_service_ext';
import {insertDataToMapCallback} from './i_idl_service_ext'; import { insertDataToMapCallback } from './i_idl_service_ext';
import IdlServiceExtStub from './idl_service_ext_stub'; import IdlServiceExtStub from './idl_service_ext_stub';
const ERR_OK = 0; const ERR_OK = 0;
...@@ -397,7 +400,7 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i ...@@ -397,7 +400,7 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i
bundleManager.getBundleNameByUid(callerUid).then((callerBundleName) => { bundleManager.getBundleNameByUid(callerUid).then((callerBundleName) => {
console.info(TAG, 'getBundleNameByUid: ' + callerBundleName); console.info(TAG, 'getBundleNameByUid: ' + callerBundleName);
// Identify the bundle name of the client. // Identify the bundle name of the client.
if (callerBundleName != 'com.example.connectextapp') { // The verification fails. if (callerBundleName != 'com.example.connectextapp') { // The verification fails.
console.info(TAG, 'The caller bundle is not in whitelist, reject'); console.info(TAG, 'The caller bundle is not in whitelist, reject');
return; return;
} }
...@@ -409,7 +412,7 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i ...@@ -409,7 +412,7 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i
insertDataToMap(key: string, val: number, callback: insertDataToMapCallback): void { insertDataToMap(key: string, val: number, callback: insertDataToMapCallback): void {
// Implement service logic. // Implement service logic.
console.log(TAG, `insertDataToMap, key: ${key} val: ${val}`); console.info(TAG, `insertDataToMap, key: ${key} val: ${val}`);
callback(ERR_OK); callback(ERR_OK);
} }
} }
...@@ -425,15 +428,15 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i ...@@ -425,15 +428,15 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i
import {processDataCallback} from './i_idl_service_ext'; import {processDataCallback} from './i_idl_service_ext';
import {insertDataToMapCallback} from './i_idl_service_ext'; import {insertDataToMapCallback} from './i_idl_service_ext';
import IdlServiceExtStub from './idl_service_ext_stub'; import IdlServiceExtStub from './idl_service_ext_stub';
const ERR_OK = 0; const ERR_OK = 0;
const ERR_DENY = -1; const ERR_DENY = -1;
const TAG: string = "[IdlServiceExtImpl]"; const TAG: string = "[IdlServiceExtImpl]";
export default class ServiceExtImpl extends IdlServiceExtStub { export default class ServiceExtImpl extends IdlServiceExtStub {
processData(data: number, callback: processDataCallback): void { processData(data: number, callback: processDataCallback): void {
console.info(TAG, `processData: ${data}`); console.info(TAG, `processData: ${data}`);
let callerTokenId = rpc.IPCSkeleton.getCallingTokenId(); let callerTokenId = rpc.IPCSkeleton.getCallingTokenId();
let accessManger = abilityAccessCtrl.createAtManager(); let accessManger = abilityAccessCtrl.createAtManager();
// The permission to be verified varies depending on the service requirements. ohos.permission.SET_WALLPAPER is only an example. // The permission to be verified varies depending on the service requirements. ohos.permission.SET_WALLPAPER is only an example.
...@@ -446,10 +449,10 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i ...@@ -446,10 +449,10 @@ When ServiceExtensionAbility is used to provide sensitive services, the client i
} }
callback(ERR_OK, data + 1); // The verification is successful, and service logic is executed normally. callback(ERR_OK, data + 1); // The verification is successful, and service logic is executed normally.
} }
insertDataToMap(key: string, val: number, callback: insertDataToMapCallback): void { insertDataToMap(key: string, val: number, callback: insertDataToMapCallback): void {
// Implement service logic. // Implement service logic.
console.log(TAG, `insertDataToMap, key: ${key} val: ${val}`); console.info(TAG, `insertDataToMap, key: ${key} val: ${val}`);
callback(ERR_OK); callback(ERR_OK);
} }
} }
......
...@@ -12,7 +12,7 @@ The following figure shows the basic concepts used in the stage model. ...@@ -12,7 +12,7 @@ The following figure shows the basic concepts used in the stage model.
The stage model provides two types of application components: UIAbility and ExtensionAbility. Both have specific classes and support object-oriented development. The stage model provides two types of application components: UIAbility and ExtensionAbility. Both have specific classes and support object-oriented development.
- UIAbility has the UI and is mainly used for user interaction. For example, with UIAbility, the Gallery application can display images in the liquid layout. After a user selects an image, it uses a new UI to display the image details. The user can touch the **Back** button to return to the liquid layout. The lifecycle of the UIAbility component contains the creation, destruction, foreground, and background states. Display-related states are exposed through WindowStage events. - UIAbility is a type of application component that provides the UI for user interaction. For example, with UIAbility, the Gallery application can display images in the liquid layout. After a user selects an image, it uses a new UI to display the image details. The user can touch the **Back** button to return to the liquid layout. The lifecycle of the UIAbility component contains the creation, destruction, foreground, and background states. Display-related states are exposed through WindowStage events.
- ExtensionAbility is oriented to specific scenarios. You cannot derive directly from ExtensionAbility. Instead, use the derived classes of ExtensionAbility for your scenarios, such as FormExtensionAbility for widget scenarios, InputMethodExtensionAbility for input method scenarios, and WorkSchedulerExtensionAbility for Work Scheduled task scenarios. For example, to enable a user to create an application widget on the home screen, you must derive FormExtensionAbility, implement the callback functions, and configure the capability in the configuration file. The derived class instances are created by developers and their lifecycles are managed by the system. In the stage model, you must use the derived classes of ExtensionAbility to develop custom services based on your service scenarios. - ExtensionAbility is oriented to specific scenarios. You cannot derive directly from ExtensionAbility. Instead, use the derived classes of ExtensionAbility for your scenarios, such as FormExtensionAbility for widget scenarios, InputMethodExtensionAbility for input method scenarios, and WorkSchedulerExtensionAbility for Work Scheduled task scenarios. For example, to enable a user to create an application widget on the home screen, you must derive FormExtensionAbility, implement the callback functions, and configure the capability in the configuration file. The derived class instances are created by developers and their lifecycles are managed by the system. In the stage model, you must use the derived classes of ExtensionAbility to develop custom services based on your service scenarios.
- [WindowStage](../windowmanager/application-window-stage.md) - [WindowStage](../windowmanager/application-window-stage.md)
...@@ -21,7 +21,7 @@ The following figure shows the basic concepts used in the stage model. ...@@ -21,7 +21,7 @@ The following figure shows the basic concepts used in the stage model.
- [Context](application-context-stage.md) - [Context](application-context-stage.md)
In the stage model, Context and its derived classes provide a variety of capabilities that can be called during the runtime. The UIAbility component and ExtensionAbility derived classes have different Context classes. These classes, which all inherit from the base class Context, provide different capabilities. In the stage model, Context and its derived classes provide a variety of resources and capabilities that can be called during the runtime. The UIAbility component and ExtensionAbility derived classes have different Context classes. These classes, which all inherit from the base class Context, provide different capabilities.
- [AbilityStage](abilitystage.md) - [AbilityStage](abilitystage.md)
...@@ -37,7 +37,7 @@ During application development based on the stage model, the following tasks are ...@@ -37,7 +37,7 @@ During application development based on the stage model, the following tasks are
| Task| Introduction| Guide| | Task| Introduction| Guide|
| -------- | -------- | -------- | | -------- | -------- | -------- |
| Application component development| Use the UIAbility and ExtensionAbility components of the stage model to develop applications.| - [Application- or Component-Level Configuration](application-component-configuration-stage.md)<br>- [UIAbility Component](uiability-overview.md)<br>- [ExtensionAbility Component](extensionability-overview.md)<br>- [AbilityStage Container Component](abilitystage.md)<br>- [Context](application-context-stage.md)<br>- [Component Startup Rules](component-startup-rules.md)| | Application component development| Use the UIAbility and ExtensionAbility components of the stage model to develop applications.| - [Application- or Component-Level Configuration](application-component-configuration-stage.md)<br>- [UIAbility Component](uiability-overview.md)<br>- [ExtensionAbility Component](extensionability-overview.md)<br>- [AbilityStage Container Component](abilitystage.md)<br>- [Context](application-context-stage.md)<br>- [Component Startup Rules](component-startup-rules.md)|
| Inter-process communication (IPC)| Learn the process model and common IPC modes of the stage model.| - [Common Events](common-event-overview.md)<br>- [Background Services](background-services.md)| | Process model| Learn the process model and common IPC modes of the stage model.| - [Common Events](common-event-overview.md)<br>- [Background Services](background-services.md)|
| Inter-thread communication| Learn the thread model and common inter-thread communication modes of the stage model.| - [Emitter](itc-with-emitter.md)<br>- [Worker](itc-with-worker.md)| | Thread model| Learn the thread model and common inter-thread communication modes of the stage model.| - [Emitter](itc-with-emitter.md)<br>- [Worker](itc-with-worker.md)|
| Mission management| Learn the basic concepts and typical scenarios of mission management in the stage model.| - [Mission Management Scenarios](mission-management-overview.md)<br>- [Mission Management and Launch Type](mission-management-launch-type.md)<br>- [Page Stack and Mission List](page-mission-stack.md)| | Mission management| Learn the basic concepts and typical scenarios of mission management in the stage model.| - [Mission Management Scenarios](mission-management-overview.md)<br>- [Mission Management and Launch Type](mission-management-launch-type.md)<br>- [Page Stack and Mission List](page-mission-stack.md)|
| Application configuration file| Learn the requirements for developing application configuration files in the stage model.| [Application Configuration File](../quick-start/application-configuration-file-overview-stage.md)| | Application configuration file| Learn the requirements for developing application configuration files in the stage model.| [Application Configuration File](config-file-stage.md)|
...@@ -12,7 +12,7 @@ import featureAbility from '@ohos.ability.featureAbility'; ...@@ -12,7 +12,7 @@ import featureAbility from '@ohos.ability.featureAbility';
async function restartAbility() { async function restartAbility() {
let wantInfo = { let wantInfo = {
bundleName: "com.sample.MyApplication", bundleName: "com.sample.MyApplication",
abilityName: "MainAbility", abilityName: "EntryAbility",
parameters: { parameters: {
page: "pages/second" page: "pages/second"
} }
...@@ -83,13 +83,13 @@ struct Index { ...@@ -83,13 +83,13 @@ struct Index {
@State message: string = 'Hello World' @State message: string = 'Hello World'
build() { build() {
// ... ...
Button("startAbility") Button("startAbility")
.onClick(() => { .onClick(() => {
featureAbility.startAbility({ featureAbility.startAbility({
want: { want: {
bundleName: "com.exm.myapplication", bundleName: "com.exm.myapplication",
abilityName: "com.exm.myapplication.MainAbility", abilityName: "com.exm.myapplication.EntryAbility",
parameters: { page: "pages/page1" } parameters: { page: "pages/page1" }
} }
}).then((data) => { }).then((data) => {
...@@ -98,13 +98,13 @@ struct Index { ...@@ -98,13 +98,13 @@ struct Index {
console.info("startAbility failed errcode:" + err.code) console.info("startAbility failed errcode:" + err.code)
}) })
}) })
// ... ...
Button("page2") Button("page2")
.onClick(() => { .onClick(() => {
featureAbility.startAbility({ featureAbility.startAbility({
want: { want: {
bundleName: "com.exm.myapplication", bundleName: "com.exm.myapplication",
abilityName: "com.exm.myapplication.MainAbility", abilityName: "com.exm.myapplication.EntryAbility",
parameters: { page: "pages/page2" } parameters: { page: "pages/page2" }
} }
}).then((data) => { }).then((data) => {
...@@ -113,7 +113,7 @@ struct Index { ...@@ -113,7 +113,7 @@ struct Index {
console.info("startAbility failed errcode:" + err.code) console.info("startAbility failed errcode:" + err.code)
}) })
}) })
// ... ...
} }
} }
``` ```
...@@ -136,7 +136,7 @@ export default { ...@@ -136,7 +136,7 @@ export default {
}) })
}, },
onDestroy() { onDestroy() {
// ... ...
}, },
} }
``` ```
...@@ -21,7 +21,7 @@ export default class EntryAbility extends UIAbility { ...@@ -21,7 +21,7 @@ export default class EntryAbility extends UIAbility {
onWindowStageCreate(windowStage) { onWindowStageCreate(windowStage) {
console.info("EntryAbility onWindowStageCreate") console.info("EntryAbility onWindowStageCreate")
windowStage.loadContent('pages/Index', (err, data) => { windowStage.loadContent('pages/Index', (err, data) => {
// ... ...
}); });
let want = { let want = {
bundleName: "com.ohos.fa", bundleName: "com.ohos.fa",
...@@ -66,7 +66,7 @@ export default class EntryAbility extends UIAbility { ...@@ -66,7 +66,7 @@ export default class EntryAbility extends UIAbility {
onWindowStageCreate(windowStage) { onWindowStageCreate(windowStage) {
console.info("EntryAbility onWindowStageCreate") console.info("EntryAbility onWindowStageCreate")
windowStage.loadContent('pages/Index', (err, data) => { windowStage.loadContent('pages/Index', (err, data) => {
// ... ...
}); });
let want = { let want = {
bundleName: "com.ohos.fa", bundleName: "com.ohos.fa",
......
...@@ -83,28 +83,31 @@ After obtaining the data synchronization permission, obtain the trusted device l ...@@ -83,28 +83,31 @@ After obtaining the data synchronization permission, obtain the trusted device l
The following sample code shows how to use **getTrustedDeviceListSync()** to obtain the trusted device list. The following sample code shows how to use **getTrustedDeviceListSync()** to obtain the trusted device list.
```ts ```ts
import deviceManager from '@ohos.distributedHardware.deviceManager'; import deviceManager from '@ohos.distributedHardware.deviceManager';
let dmClass;
let dmClass;
function getDeviceManager() { function getDeviceManager() {
deviceManager.createDeviceManager('ohos.example.distributedService', (error, dm) => { deviceManager.createDeviceManager('ohos.example.distributedService', (error, dm) => {
if (error) { if (error) {
console.info('create device manager failed with ' + error) console.info('create device manager failed with ' + error)
} }
dmClass = dm; dmClass = dm;
}) })
} }
function getRemoteDeviceId() {
if (typeof dmClass === 'object' && dmClass != null) { function getRemoteDeviceId() {
let list = dmClass.getTrustedDeviceListSync(); if (typeof dmClass === 'object' && dmClass != null) {
if (typeof (list) == 'undefined' || typeof (list.length) == 'undefined') { let list = dmClass.getTrustedDeviceListSync();
console.info("EntryAbility onButtonClick getRemoteDeviceId err: list is null"); if (typeof (list) == 'undefined' || typeof (list.length) == 'undefined') {
return; console.info("EntryAbility onButtonClick getRemoteDeviceId err: list is null");
} return;
console.info("EntryAbility onButtonClick getRemoteDeviceId success:" + list[0].deviceId); }
return list[0].deviceId; console.info("EntryAbility onButtonClick getRemoteDeviceId success:" + list[0].deviceId);
} else { return list[0].deviceId;
console.info("EntryAbility onButtonClick getRemoteDeviceId err: dmClass is null"); } else {
} console.info("EntryAbility onButtonClick getRemoteDeviceId err: dmClass is null");
}
} }
``` ```
...@@ -116,21 +119,22 @@ The following sample code shows how to explicitly start a remote PageAbility thr ...@@ -116,21 +119,22 @@ The following sample code shows how to explicitly start a remote PageAbility thr
```ts ```ts
import featureAbility from '@ohos.ability.featureAbility'; import featureAbility from '@ohos.ability.featureAbility';
function onStartRemoteAbility() {
console.info('onStartRemoteAbility begin'); function onStartRemoteAbility() {
let params; console.info('onStartRemoteAbility begin');
let wantValue = { let params;
bundleName: 'ohos.samples.etsDemo', let wantValue = {
abilityName: 'ohos.samples.etsDemo.RemoteAbility', bundleName: 'ohos.samples.etsDemo',
deviceId: getRemoteDeviceId(), // getRemoteDeviceId is defined in the preceding sample code. abilityName: 'ohos.samples.etsDemo.RemoteAbility',
parameters: params deviceId: getRemoteDeviceId(), // getRemoteDeviceId is defined in the preceding sample code.
}; parameters: params
console.info('onStartRemoteAbility want=' + JSON.stringify(wantValue)); };
featureAbility.startAbility({ console.info('onStartRemoteAbility want=' + JSON.stringify(wantValue));
want: wantValue featureAbility.startAbility({
}).then((data) => { want: wantValue
console.info('onStartRemoteAbility finished, ' + JSON.stringify(data)); }).then((data) => {
}); console.info('onStartRemoteAbility finished, ' + JSON.stringify(data));
console.info('onStartRemoteAbility end'); });
console.info('onStartRemoteAbility end');
} }
``` ```
...@@ -27,7 +27,7 @@ async function startServiceAbility() { ...@@ -27,7 +27,7 @@ async function startServiceAbility() {
``` ```
In the preceding code, **startAbility()** is used to start the ServiceAbility. In the preceding code, [startAbility()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextstartability) is used to start the ServiceAbility.
- If the ServiceAbility is not running, the system calls **onStart()** to initialize the ServiceAbility, and then calls **onCommand()** on the ServiceAbility. - If the ServiceAbility is not running, the system calls **onStart()** to initialize the ServiceAbility, and then calls **onCommand()** on the ServiceAbility.
......
...@@ -54,7 +54,7 @@ In OpenHarmony, you can subscribe to system environment variable changes in the ...@@ -54,7 +54,7 @@ In OpenHarmony, you can subscribe to system environment variable changes in the
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
...@@ -77,7 +77,7 @@ In OpenHarmony, you can subscribe to system environment variable changes in the ...@@ -77,7 +77,7 @@ In OpenHarmony, you can subscribe to system environment variable changes in the
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
...@@ -99,19 +99,19 @@ import AbilityStage from '@ohos.app.ability.AbilityStage'; ...@@ -99,19 +99,19 @@ import AbilityStage from '@ohos.app.ability.AbilityStage';
let systemLanguage: string; // System language in use. let systemLanguage: string; // System language in use.
export default class MyAbilityStage extends AbilityStage { export default class MyAbilityStage extends AbilityStage {
onCreate() { onCreate() {
systemLanguage = this.context.config.language; // Obtain the system language in use when the AbilityStage instance is loaded for the first time. systemLanguage = this.context.config.language; // Obtain the system language in use when the AbilityStage instance is loaded for the first time.
console.info(`systemLanguage is ${systemLanguage} `); console.info(`systemLanguage is ${systemLanguage} `);
} }
onConfigurationUpdate(newConfig) { onConfigurationUpdate(newConfig) {
console.info(`onConfigurationUpdated systemLanguage is ${systemLanguage}, newConfig: ${JSON.stringify(newConfig)}`); console.info(`onConfigurationUpdated systemLanguage is ${systemLanguage}, newConfig: ${JSON.stringify(newConfig)}`);
if (systemLanguage !== newConfig.language) { if (systemLanguage !== newConfig.language) {
console.info(`systemLanguage from ${systemLanguage} changed to ${newConfig.language}`); console.info(`systemLanguage from ${systemLanguage} changed to ${newConfig.language}`);
systemLanguage = newConfig.language; // Save the new system language as the system language in use, which will be used for comparison. systemLanguage = newConfig.language; // Save the new system language as the system language in use, which will be used for comparison.
}
} }
}
} }
``` ```
...@@ -131,21 +131,21 @@ import UIAbility from '@ohos.app.ability.UIAbility'; ...@@ -131,21 +131,21 @@ import UIAbility from '@ohos.app.ability.UIAbility';
let systemLanguage: string; // System language in use. let systemLanguage: string; // System language in use.
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
onCreate(want, launchParam) { onCreate(want, launchParam) {
systemLanguage = this.context.config.language; // Obtain the system language in use when the UIAbility instance is loaded for the first time. systemLanguage = this.context.config.language; // Obtain the system language in use when the UIAbility instance is loaded for the first time.
console.info(`systemLanguage is ${systemLanguage} `); console.info(`systemLanguage is ${systemLanguage} `);
} }
onConfigurationUpdate(newConfig) { onConfigurationUpdate(newConfig) {
console.info(`onConfigurationUpdated systemLanguage is ${systemLanguage}, newConfig: ${JSON.stringify(newConfig)}`); console.info(`onConfigurationUpdated systemLanguage is ${systemLanguage}, newConfig: ${JSON.stringify(newConfig)}`);
if (systemLanguage !== newConfig.language) { if (systemLanguage !== newConfig.language) {
console.info(`systemLanguage from ${systemLanguage} changed to ${newConfig.language}`); console.info(`systemLanguage from ${systemLanguage} changed to ${newConfig.language}`);
systemLanguage = newConfig.language; // Save the new system language as the system language in use, which will be used for comparison. systemLanguage = newConfig.language; // Save the new system language as the system language in use, which will be used for comparison.
}
} }
}
// ... ...
} }
``` ```
...@@ -163,10 +163,10 @@ The code snippet below uses FormExtensionAbility as an example to describe how t ...@@ -163,10 +163,10 @@ The code snippet below uses FormExtensionAbility as an example to describe how t
import FormExtensionAbility from '@ohos.app.form.FormExtensionAbility'; import FormExtensionAbility from '@ohos.app.form.FormExtensionAbility';
export default class EntryFormAbility extends FormExtensionAbility { export default class EntryFormAbility extends FormExtensionAbility {
onConfigurationUpdate(newConfig) { onConfigurationUpdate(newConfig) {
console.info(`newConfig is ${JSON.stringify(newConfig)}`); console.info(`newConfig is ${JSON.stringify(newConfig)}`);
} }
// ... ...
} }
``` ```
# Thread Model Overview (FA Model) # Thread Model Overview (FA Model)
There are three types of threads in the FA model: There are three types of threads in the FA model:
- Main thread - Main thread
Manages other threads. Manages other threads.
- Ability thread - Ability thread
- One ability thread for each ability. - One ability thread for each ability.
- Distributes input events. - Distributes input events.
...@@ -16,13 +14,11 @@ There are three types of threads in the FA model: ...@@ -16,13 +14,11 @@ There are three types of threads in the FA model:
- Receives messages sent by the worker thread. - Receives messages sent by the worker thread.
- Worker thread - Worker thread
Performs time-consuming operations Performs time-consuming operations
Based on the OpenHarmony thread model, different services run on different threads. Service interaction requires inter-thread communication. Threads can communicate with each other in Emitter or Worker mode. Emitter is mainly used for event synchronization between threads, and Worker is mainly used to execute time-consuming tasks. Based on the OpenHarmony thread model, different services run on different threads. Service interaction requires inter-thread communication. Threads can communicate with each other in Emitter or Worker mode. Emitter is mainly used for event synchronization between threads, and Worker is mainly used to execute time-consuming tasks.
> **NOTE** > **NOTE**
> >
> The FA model provides an independent thread for each ability. Emitter is mainly used for event synchronization within the ability thread, between a pair of ability threads, or between the ability thread and worker thread. > The FA model provides an independent thread for each ability. Emitter is mainly used for event synchronization within the ability thread, between a pair of ability threads, or between the ability thread and worker thread.
...@@ -17,5 +17,6 @@ Based on the OpenHarmony thread model, different services run on different threa ...@@ -17,5 +17,6 @@ Based on the OpenHarmony thread model, different services run on different threa
> **NOTE** > **NOTE**
> >
> - The stage model provides only the main thread and worker thread. Emitter is mainly used for event synchronization within the main thread or between the main thread and worker thread. > - The stage model provides only the main thread and worker thread. Emitter is mainly used for event synchronization within the worker thread or between the main thread and worker thread.
> - To view thread information about an application process, run the **hdc shell** command to enter the shell CLI of the device, and then run the **ps -p *<pid>* -T command**, where *<pid>* indicates the ID of the application process. > - The UIAbility and UI are in the main thread. For details about data synchronization between them, see [Data Synchronization Between UIAbility and UI](uiability-data-sync-with-ui.md).
> - To view thread information about an application process, run the **hdc shell** command to enter the shell CLI of the device, and then run the **ps -p *<pid>* -T command**, where *<pid>* indicates the [process ID](process-model-stage.md) of the application.
...@@ -3,17 +3,16 @@ ...@@ -3,17 +3,16 @@
Based on the OpenHarmony application model, you can use any of the following ways to implement data synchronization between the UIAbility component and UI: Based on the OpenHarmony application model, you can use any of the following ways to implement data synchronization between the UIAbility component and UI:
- EventHub: The [base class Context](application-context-stage.md) provides the EventHub capability. It is implemented based on the publish/subscribe (pub/sub) pattern. Your application subscribes to an event and when the event occurs, receives a notification. - [Using EventHub for Data Synchronization](#using-eventhub-for-data-synchronization): The **EventHub** object is provided by the base class **Context**. Events are transferred using the publish/subscribe (pub/sub) pattern. Specifically, after subscribing to an event, your application will receive the event and process it accordingly when the event is published.
- [Using globalThis for Data Synchronization](#using-globalthis-for-data-synchronization): **globalThis** is a global object inside the ArkTS engine instance and can be accessed by components such as UIAbility, ExtensionAbility, and Page.
- globalThis: It is a global object accessible in the ArkTS engine instance. - [Using AppStorage or LocalStorage for Data Synchronization](#using-appstorage-or-localstorage-for-data-synchronization): ArkUI provides two application-level state management solutions: AppStorage and LocalStorage, which implement application- and UIAbility-level data synchronization, respectively.
- LocalStorage/AppStorage: See [State Management of Application-Level Variables](../quick-start/arkts-state-mgmt-application-level.md).
## Using EventHub for Data Synchronization ## Using EventHub for Data Synchronization
[EventHub](../reference/apis/js-apis-inner-application-eventHub.md) provides an event mechanism at the UIAbility or ExtensionAbility component level. Centered on the UIAbility or ExtensionAbility component, EventHub provides data communication capabilities for subscribing to, unsubscribing from, and triggering events. [EventHub](../reference/apis/js-apis-inner-application-eventHub.md) provides an event mechanism for the UIAbility or ExtensionAbility component so that they can subscribe to, unsubscribe from, and trigger events.
Before using EventHub, you must obtain an EventHub object, which is provided by the [base class Context](application-context-stage.md). This section uses EventHub as an example to describe how to implement data synchronization between the UIAbility component and the UI. Before using the APIs provided by **EventHub**, you must obtain an **EventHub** object, which is provided by the [base class Context](application-context-stage.md). This section uses EventHub as an example to describe how to implement data synchronization between the UIAbility component and the UI.
1. Call [eventHub.on()](../reference/apis/js-apis-inner-application-eventHub.md#eventhubon) in the UIAbility in either of the following ways to register a custom event **event1**. 1. Call [eventHub.on()](../reference/apis/js-apis-inner-application-eventHub.md#eventhubon) in the UIAbility in either of the following ways to register a custom event **event1**.
...@@ -23,21 +22,21 @@ Before using EventHub, you must obtain an EventHub object, which is provided by ...@@ -23,21 +22,21 @@ Before using EventHub, you must obtain an EventHub object, which is provided by
const TAG: string = '[Example].[Entry].[EntryAbility]'; const TAG: string = '[Example].[Entry].[EntryAbility]';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
func1(...data) { func1(...data) {
// Trigger the event to complete the service operation. // Trigger the event to complete the service operation.
console.info(TAG, '1. ' + JSON.stringify(data)); console.info(TAG, '1. ' + JSON.stringify(data));
} }
onCreate(want, launch) { onCreate(want, launch) {
// Obtain an eventHub object. // Obtain an eventHub object.
let eventhub = this.context.eventHub; let eventhub = this.context.eventHub;
// Subscribe to the event. // Subscribe to the event.
eventhub.on('event1', this.func1); eventhub.on('event1', this.func1);
eventhub.on('event1', (...data) => { eventhub.on('event1', (...data) => {
// Trigger the event to complete the service operation. // Trigger the event to complete the service operation.
console.info(TAG, '2. ' + JSON.stringify(data)); console.info(TAG, '2. ' + JSON.stringify(data));
}); });
} }
} }
``` ```
...@@ -63,7 +62,7 @@ Before using EventHub, you must obtain an EventHub object, which is provided by ...@@ -63,7 +62,7 @@ Before using EventHub, you must obtain an EventHub object, which is provided by
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
...@@ -81,44 +80,42 @@ Before using EventHub, you must obtain an EventHub object, which is provided by ...@@ -81,44 +80,42 @@ Before using EventHub, you must obtain an EventHub object, which is provided by
4. After **event1** is used, you can call [eventHub.off()](../reference/apis/js-apis-inner-application-eventHub.md#eventhuboff) to unsubscribe from the event. 4. After **event1** is used, you can call [eventHub.off()](../reference/apis/js-apis-inner-application-eventHub.md#eventhuboff) to unsubscribe from the event.
```ts ```ts
// context is the ability context of the UIAbility instance. // context is the AbilityContext of the UIAbility instance.
this.context.eventHub.off('event1'); this.context.eventHub.off('event1');
``` ```
## Using globalThis for Data Synchronization ## Using globalThis for Data Synchronization
**globalThis** is a global object inside the [ArkTS engine instance](thread-model-stage.md) and can be used by UIAbility, ExtensionAbility, and Page inside the engine. Therefore, you can use **globalThis** for data synchronization. **globalThis** is a global object inside the [ArkTS engine instance](thread-model-stage.md) and can be used by UIAbility, ExtensionAbility, and Page inside the engine. Therefore, you can use **globalThis** for data synchronization.
**Figure 1** Using globalThis for data synchronization **Figure 1** Using globalThis for data synchronization
![globalThis1](figures/globalThis1.png)
![globalThis1](figures/globalThis1.png)
The following describes how to use **globalThis** in three scenarios. Precautions are provided as well. The following describes how to use **globalThis** in three scenarios. Precautions are provided as well.
- [Using globalThis Between UIAbility and Page](#using-globalthis-between-uiability-and-page) - [Using globalThis Between UIAbility and Page](#using-globalthis-between-uiability-and-page)
- [Using globalThis Between UIAbility and UIAbility](##using-globalthis-between-uiability-and-uiability) - [Using globalThis Between UIAbility and UIAbility](#using-globalthis-between-uiability-and-uiability)
- [Use globalThis Between UIAbility and ExtensionAbility](#using-globalthis-between-uiability-and-extensionability) - [Use globalThis Between UIAbility and ExtensionAbility](#using-globalthis-between-uiability-and-extensionability)
- [Precautions for Using globalThis](#precautions-for-using-globalthis) - [Precautions for Using globalThis](#precautions-for-using-globalthis)
### Using globalThis Between UIAbility and Page ### Using globalThis Between UIAbility and Page
You can use **globalThis** to bind attributes or methods to implement data synchronization between the UIAbility component and UI. For example, if you bind the **want** parameter in the UIAbility component, you can use the **want** parameter information on the UI corresponding to the UIAbility component. By binding attributes or methods to **globalThis**, you can implement data synchronization between the UIAbility component and UI. For example, if you bind the **want** parameter in the UIAbility component, you can use the **want** parameter information on the UI corresponding to the UIAbility component.
1. When **startAbility()** is called to start a UIAbility instance, the **onCreate()** callback is invoked, and the **want** parameter can be passed in the callback. Therefore, you can bind the **want** parameter to **globalThis**. 1. When [startAbility()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextstartability) is called to start a UIAbility instance, the [onCreate()](../reference/apis/js-apis-app-ability-uiAbility.md#uiabilityoncreate) callback is invoked, and the **want** parameter can be passed in the callback. Therefore, you can bind the **want** parameter to **globalThis**.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility' import UIAbility from '@ohos.app.ability.UIAbility';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
onCreate(want, launch) { onCreate(want, launch) {
globalThis.entryAbilityWant = want; globalThis.entryAbilityWant = want;
// ... ...
} }
// ... ...
} }
``` ```
...@@ -136,7 +133,7 @@ You can use **globalThis** to bind attributes or methods to implement data synch ...@@ -136,7 +133,7 @@ You can use **globalThis** to bind attributes or methods to implement data synch
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
...@@ -144,51 +141,51 @@ You can use **globalThis** to bind attributes or methods to implement data synch ...@@ -144,51 +141,51 @@ You can use **globalThis** to bind attributes or methods to implement data synch
### Using globalThis Between UIAbility and UIAbility ### Using globalThis Between UIAbility and UIAbility
To implement data synchronization between two UIAbility components in the same application, you can bind data to **globalThis**. For example, you can save data in **globalThis** in AbilityA and obtain the data from AbilityB. To implement data synchronization between two UIAbility components in the same application, you can bind data to **globalThis**. For example, you can save data in **globalThis** in UIAbilityA and obtain the data from UIAbilityB.
1. AbilityA stores a string and binds it to globalThis. 1. UIAbilityA stores a string and binds it to globalThis.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility' import UIAbility from '@ohos.app.ability.UIAbility'
export default class AbilityA extends UIAbility { export default class UIAbilityA extends UIAbility {
onCreate(want, launch) { onCreate(want, launch) {
globalThis.entryAbilityStr = 'AbilityA'; // AbilityA stores the string "AbilityA" to globalThis. globalThis.entryAbilityStr = 'UIAbilityA'; // UIAbilityA stores the string "UIAbilityA" to globalThis.
// ... ...
} }
} }
``` ```
2. Obtain the data from AbilityB. 2. Obtain the data from UIAbilityB.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility' import UIAbility from '@ohos.app.ability.UIAbility'
export default class AbilityB extends UIAbility { export default class UIAbilityB extends UIAbility {
onCreate(want, launch) { onCreate(want, launch) {
// AbilityB reads the name from globalThis and outputs it. // UIAbilityB reads name from globalThis and outputs it.
console.info('name from entryAbilityStr: ' + globalThis.entryAbilityStr); console.info('name from entryAbilityStr: ' + globalThis.entryAbilityStr);
// ... ...
} }
} }
``` ```
### Using globalThis Between UIAbility and ExtensionAbility ### Using globalThis Between UIAbility and ExtensionAbility
To implement data synchronization between the UIAbility and ExtensionAbility components in the same application, you can bind data to **globalThis**. For example, you can save data in **globalThis** in AbilityA and obtain the data from ServiceExtensionAbility. To implement data synchronization between the UIAbility and ExtensionAbility components in the same application, you can bind data to **globalThis**. For example, you can save data in **globalThis** in UIAbilityA and obtain the data from ServiceExtensionAbility.
1. AbilityA stores a string and binds it to globalThis. 1. UIAbilityA stores a string and binds it to globalThis.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility' import UIAbility from '@ohos.app.ability.UIAbility'
export default class AbilityA extends UIAbility { export default class UIAbilityA extends UIAbility {
onCreate(want, launch) { onCreate(want, launch) {
// AbilityA stores the string "AbilityA" to globalThis. // UIAbilityA stores the string "UIAbilityA" to globalThis.
globalThis.entryAbilityStr = 'AbilityA'; globalThis.entryAbilityStr = 'UIAbilityA';
// ... ...
} }
} }
``` ```
...@@ -198,22 +195,21 @@ To implement data synchronization between the UIAbility and ExtensionAbility com ...@@ -198,22 +195,21 @@ To implement data synchronization between the UIAbility and ExtensionAbility com
import Extension from '@ohos.app.ability.ServiceExtensionAbility' import Extension from '@ohos.app.ability.ServiceExtensionAbility'
export default class ServiceExtAbility extends Extension { export default class ServiceExtAbility extends Extension {
onCreate(want) { onCreate(want) {
/ / ServiceExtAbility reads name from globalThis and outputs it. / / ServiceExtAbility reads name from globalThis and outputs it.
console.info('name from entryAbilityStr: ' + globalThis.entryAbilityStr); console.info('name from entryAbilityStr: ' + globalThis.entryAbilityStr);
// ... ...
} }
} }
``` ```
### Precautions for Using globalThis ### Precautions for Using globalThis
**Figure 2** Precautions for globalThis **Figure 2** Precautions for globalThis
![globalThis2](figures/globalThis2.png) ![globalThis2](figures/globalThis2.png)
- In the stage model, all the UIAbility components in a process share one ArkTS engine instance. When using **globalThis**, do not store objects with the same name. For example, if AbilityA and AbilityB use **globalThis** to store two objects with the same name, the object stored earlier will be overwritten. - In the stage model, all the UIAbility components in a process share one ArkTS engine instance. When using **globalThis**, do not store objects with the same name. For example, if UIAbilityA and UIAbilityB use **globalThis** to store two objects with the same name, the object stored earlier will be overwritten.
- This problem does not occur in the FA model because each UIAbility component uses an independent engine. - This problem does not occur in the FA model because each UIAbility component uses an independent engine.
...@@ -221,20 +217,20 @@ To implement data synchronization between the UIAbility and ExtensionAbility com ...@@ -221,20 +217,20 @@ To implement data synchronization between the UIAbility and ExtensionAbility com
The following provides an example to describe the object overwritten problem in the stage model. The following provides an example to describe the object overwritten problem in the stage model.
1. In the AbilityA file, [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) is stored in **globalThis**. 1. In the UIAbilityA file, [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) is stored in **globalThis**.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility' import UIAbility from '@ohos.app.ability.UIAbility'
export default class AbilityA extends UIAbility { export default class UIAbilityA extends UIAbility {
onCreate(want, launch) { onCreate(want, launch) {
globalThis.context = this.context; // AbilityA stores the context in globalThis. globalThis.context = this.context; // UIAbilityA stores the context in globalThis.
// ... ...
} }
} }
``` ```
2. Obtain and use [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) on the page of Ability A. After the AbilityA instance is used, switch it to the background. 2. Obtain and use [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) on the page of UIAbilityA. After the UIAbilityA instance is used, switch it to the background.
```ts ```ts
@Entry @Entry
...@@ -242,33 +238,29 @@ The following provides an example to describe the object overwritten problem in ...@@ -242,33 +238,29 @@ The following provides an example to describe the object overwritten problem in
struct Index { struct Index {
onPageShow() { onPageShow() {
let ctx = globalThis.context; // Obtain the context from globalThis and use it. let ctx = globalThis.context; // Obtain the context from globalThis and use it.
let permissions = ['com.example.permission']
ctx.requestPermissionsFromUser(permissions,(result) => {
// ...
});
} }
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
3. In the AbilityB file, [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) is stored in **globalThis** and has the same name as that in the AbilityA file. 3. In the UIAbilityB file, [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) is stored in **globalThis** and has the same name as that in the UIAbilityA file.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility' import UIAbility from '@ohos.app.ability.UIAbility'
export default class AbilityB extends UIAbility { export default class UIAbilityB extends UIAbility {
onCreate(want, launch) { onCreate(want, launch) {
// AbilityB overwrites the context stored by AbilityA in globalThis. // UIAbilityB overwrites the context stored by UIAbilityA in globalThis.
globalThis.context = this.context; globalThis.context = this.context;
// ... ...
} }
} }
``` ```
4. Obtain and use [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) on the page of Ability B. The obtained **globalThis.context** is the value of [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) in AbilityB. 4. Obtain and use [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) on the page of UIAbilityB. The obtained **globalThis.context** is the value of [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) in UIAbilityB.
```ts ```ts
@Entry @Entry
...@@ -276,47 +268,43 @@ The following provides an example to describe the object overwritten problem in ...@@ -276,47 +268,43 @@ The following provides an example to describe the object overwritten problem in
struct Index { struct Index {
onPageShow() { onPageShow() {
let ctx = globalThis.context; // Obtain the context from globalThis and use it. let ctx = globalThis.context; // Obtain the context from globalThis and use it.
let permissions = ['com.example.permission']
ctx.requestPermissionsFromUser(permissions,(result) => {
console.info('requestPermissionsFromUser result:' + JSON.stringify(result));
});
} }
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
5. Switch the AbilityB instance to the background and switch the AbilityA instance to the foreground. In this case, AbilityA will not enter the **onCreate()** lifecycle again. 5. Switch the UIAbilityB instance to the background and switch the UIAbilityA instance to the foreground. In this case, UIAbilityA will not enter the **onCreate()** lifecycle again.
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility' import UIAbility from '@ohos.app.ability.UIAbility'
export default class AbilityA extends UIAbility { export default class UIAbilityA extends UIAbility {
onCreate(want, launch) { // AbilityA will not enter this lifecycle. onCreate(want, launch) { // UIAbilityA will not enter this lifecycle.
globalThis.context = this.context; globalThis.context = this.context;
// ... ...
} }
} }
``` ```
6. When the page of AbilityA is displayed, the obtained **globalThis.context** is [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) of AbilityB instead of AbilityA. An error occurs. 6. When the page of UIAbilityA is displayed, the obtained **globalThis.context** is [UIAbilityContext](../reference/apis/js-apis-inner-application-uiAbilityContext.md) of UIAbilityB instead of UIAbilityA. An error occurs.
```ts ```ts
@Entry @Entry
@Component @Component
struct Index { struct Index {
onPageShow() { onPageShow() {
let ctx = globalThis.context; // The context in globalThis is the context of AbilityB. let ctx = globalThis.context; // The context in globalThis is the context of UIAbilityB.
let permissions=['com.example.permission'];
ctx.requestPermissionsFromUser(permissions,(result) => { // Using this object causes a process breakdown.
console.info('requestPermissionsFromUser result:' + JSON.stringify(result));
});
} }
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
## Using AppStorage or LocalStorage for Data Synchronization
ArkUI provides AppStorage and LocalStorage to implement application- and UIAbility-level data synchronization, respectively. Both solutions can be used to manage the application state, enhance application performance, and improve user experience. The AppStorage is a global state manager and is applicable when multiple UIAbilities share the same state data. The LocalStorage is a local state manager that manages state data used inside a single UIAbility. They help you control the application state more flexibly and improve the maintainability and scalability of applications. For details, see [State Management of Application-Level Variables](../quick-start/arkts-application-state-management-overview.md).
...@@ -17,7 +17,8 @@ The launch type of the UIAbility component refers to the state of the UIAbility ...@@ -17,7 +17,8 @@ The launch type of the UIAbility component refers to the state of the UIAbility
Each time [startAbility()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextstartability) is called, if a UIAbility instance of this type already exists in the application process, the instance is reused. Therefore, only one UIAbility instance of this type exists in the system, that is, displayed in **Recents**. Each time [startAbility()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextstartability) is called, if a UIAbility instance of this type already exists in the application process, the instance is reused. Therefore, only one UIAbility instance of this type exists in the system, that is, displayed in **Recents**.
**Figure 1** Demonstration effect in singleton mode **Figure 1** Demonstration effect in singleton mode
![uiability-launch-type1](figures/uiability-launch-type1.gif) ![uiability-launch-type1](figures/uiability-launch-type1.gif)
> **NOTE** > **NOTE**
...@@ -30,11 +31,11 @@ To use the singleton mode, set **launchType** in the [module.json5 configuration ...@@ -30,11 +31,11 @@ To use the singleton mode, set **launchType** in the [module.json5 configuration
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
"launchType": "singleton", "launchType": "singleton",
// ... ...
} }
] ]
} }
...@@ -56,11 +57,11 @@ To use the multiton mode, set **launchType** in the [module.json5 file](../quick ...@@ -56,11 +57,11 @@ To use the multiton mode, set **launchType** in the [module.json5 file](../quick
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
"launchType": "multiton", "launchType": "multiton",
// ... ...
} }
] ]
} }
...@@ -73,6 +74,7 @@ To use the multiton mode, set **launchType** in the [module.json5 file](../quick ...@@ -73,6 +74,7 @@ To use the multiton mode, set **launchType** in the [module.json5 file](../quick
The **specified** mode is used in some special scenarios. For example, in a document application, you want a document instance to be created each time you create a document, but you want to use the same document instance when you repeatedly open an existing document. The **specified** mode is used in some special scenarios. For example, in a document application, you want a document instance to be created each time you create a document, but you want to use the same document instance when you repeatedly open an existing document.
**Figure 3** Demonstration effect in specified mode **Figure 3** Demonstration effect in specified mode
![uiability-launch-type3](figures/uiability-launch-type3.gif) ![uiability-launch-type3](figures/uiability-launch-type3.gif)
For example, there are two UIAbility components: EntryAbility and SpecifiedAbility (with the launch type **specified**). You are required to start SpecifiedAbility from EntryAbility. For example, there are two UIAbility components: EntryAbility and SpecifiedAbility (with the launch type **specified**). You are required to start SpecifiedAbility from EntryAbility.
...@@ -82,11 +84,11 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili ...@@ -82,11 +84,11 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
"launchType": "specified", "launchType": "specified",
// ... ...
} }
] ]
} }
...@@ -99,23 +101,24 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili ...@@ -99,23 +101,24 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili
// Configure an independent key for each UIAbility instance. // Configure an independent key for each UIAbility instance.
// For example, in the document usage scenario, use the document path as the key. // For example, in the document usage scenario, use the document path as the key.
function getInstance() { function getInstance() {
// ... ...
} }
let context =...; // context is the UIAbilityContext of the initiator UIAbility.
let want = { let want = {
deviceId: '', // An empty deviceId indicates the local device. deviceId: '', // An empty deviceId indicates the local device.
bundleName: 'com.example.myapplication', bundleName: 'com.example.myapplication',
abilityName: 'SpecifiedAbility', abilityName: 'SpecifiedAbility',
moduleName: 'module1', // moduleName is optional. moduleName: 'specified', // moduleName is optional.
parameters: {// Custom information. parameters: {// Custom information.
instanceKey: getInstance(), instanceKey: getInstance(),
}, },
} }
// context is the UIAbilityContext of the initiator UIAbility.
this.context.startAbility(want).then(() => { context.startAbility(want).then(() => {
// ... console.info('Succeeded in starting ability.');
}).catch((err) => { }).catch((err) => {
// ... console.error(`Failed to start ability. Code is ${err.code}, message is ${err.message}`);
}) })
``` ```
...@@ -127,16 +130,16 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili ...@@ -127,16 +130,16 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili
import AbilityStage from '@ohos.app.ability.AbilityStage'; import AbilityStage from '@ohos.app.ability.AbilityStage';
export default class MyAbilityStage extends AbilityStage { export default class MyAbilityStage extends AbilityStage {
onAcceptWant(want): string { onAcceptWant(want): string {
// In the AbilityStage instance of the callee, a key value corresponding to a UIAbility instance is returned for UIAbility whose launch type is specified. // In the AbilityStage instance of the callee, a key value corresponding to a UIAbility instance is returned for UIAbility whose launch type is specified.
// In this example, SpecifiedAbility of module1 is returned. // In this example, SpecifiedAbility of module1 is returned.
if (want.abilityName === 'SpecifiedAbility') { if (want.abilityName === 'SpecifiedAbility') {
// The returned key string is a custom string. // The returned key string is a custom string.
return `SpecifiedAbilityInstance_${want.parameters.instanceKey}`; return `SpecifiedAbilityInstance_${want.parameters.instanceKey}`;
}
return '';
} }
return '';
}
} }
``` ```
...@@ -153,3 +156,4 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili ...@@ -153,3 +156,4 @@ For example, there are two UIAbility components: EntryAbility and SpecifiedAbili
2. Close the process of file A in **Recents**. UIAbility instance 1 is destroyed. Return to the home screen and open file A again. A new UIAbility instance is started, for example, UIAbility instance 2. 2. Close the process of file A in **Recents**. UIAbility instance 1 is destroyed. Return to the home screen and open file A again. A new UIAbility instance is started, for example, UIAbility instance 2.
3. Return to the home screen and open file B. A new UIAbility instance is started, for example, UIAbility instance 3. 3. Return to the home screen and open file B. A new UIAbility instance is started, for example, UIAbility instance 3.
4. Return to the home screen and open file A again. UIAbility instance 2 is started. This is because the system automatically matches the key of the UIAbility instance and starts the UIAbility instance that has a matching key. In this example, UIAbility instance 2 has the same key as file A. Therefore, the system pulls back UIAbility instance 2 and focuses it without creating a new instance. 4. Return to the home screen and open file A again. UIAbility instance 2 is started. This is because the system automatically matches the key of the UIAbility instance and starts the UIAbility instance that has a matching key. In this example, UIAbility instance 2 has the same key as file A. Therefore, the system pulls back UIAbility instance 2 and focuses it without creating a new instance.
...@@ -8,8 +8,7 @@ When a user opens, switches, and returns to an application, the UIAbility instan ...@@ -8,8 +8,7 @@ When a user opens, switches, and returns to an application, the UIAbility instan
The lifecycle of UIAbility has four states: **Create**, **Foreground**, **Background**, and **Destroy**, as shown in the figure below. The lifecycle of UIAbility has four states: **Create**, **Foreground**, **Background**, and **Destroy**, as shown in the figure below.
**Figure 1** UIAbility lifecycle states **Figure 1** UIAbility lifecycle states
![Ability-Life-Cycle](figures/Ability-Life-Cycle.png)
![Ability-Life-Cycle](figures/Ability-Life-Cycle.png)
## Description of Lifecycle States ## Description of Lifecycle States
...@@ -22,24 +21,25 @@ The **Create** state is triggered when the UIAbility instance is created during ...@@ -22,24 +21,25 @@ The **Create** state is triggered when the UIAbility instance is created during
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility'; import UIAbility from '@ohos.app.ability.UIAbility';
import window from '@ohos.window';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
onCreate(want, launchParam) { onCreate(want, launchParam) {
// Initialize the application. // Initialize the application.
} }
// ... ...
} }
``` ```
> **NOTE**
>
> [Want](../reference/apis/js-apis-app-ability-want.md) is used as the carrier to transfer information between application components. For details, see [Want](want-overview.md).
### WindowStageCreate and WindowStageDestory ### WindowStageCreate and WindowStageDestory
After the UIAbility instance is created but before it enters the **Foreground** state, the system creates a WindowStage instance and triggers the **onWindowStageCreate()** callback. You can set UI loading and WindowStage event subscription in the callback. After the UIAbility instance is created but before it enters the **Foreground** state, the system creates a WindowStage instance and triggers the **onWindowStageCreate()** callback. You can set UI loading and WindowStage event subscription in the callback.
**Figure 2** WindowStageCreate and WindowStageDestory **Figure 2** WindowStageCreate and WindowStageDestory
![Ability-Life-Cycle-WindowStage](figures/Ability-Life-Cycle-WindowStage.png)
![Ability-Life-Cycle-WindowStage](figures/Ability-Life-Cycle-WindowStage.png)
In the **onWindowStageCreate()** callback, use [loadContent()](../reference/apis/js-apis-window.md#loadcontent9-2) to set the page to be loaded, and call [on('windowStageEvent')](../reference/apis/js-apis-window.md#onwindowstageevent9) to subscribe to [WindowStage events](../reference/apis/js-apis-window.md#windowstageeventtype9), for example, having or losing focus, or becoming visible or invisible. In the **onWindowStageCreate()** callback, use [loadContent()](../reference/apis/js-apis-window.md#loadcontent9-2) to set the page to be loaded, and call [on('windowStageEvent')](../reference/apis/js-apis-window.md#onwindowstageevent9) to subscribe to [WindowStage events](../reference/apis/js-apis-window.md#windowstageeventtype9), for example, having or losing focus, or becoming visible or invisible.
...@@ -48,25 +48,40 @@ import UIAbility from '@ohos.app.ability.UIAbility'; ...@@ -48,25 +48,40 @@ import UIAbility from '@ohos.app.ability.UIAbility';
import window from '@ohos.window'; import window from '@ohos.window';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
// ... ...
onWindowStageCreate(windowStage: Window.WindowStage) { onWindowStageCreate(windowStage: window.WindowStage) {
// Subscribe to the WindowStage events (having or losing focus, or becoming visible or invisible). // Subscribe to the WindowStage events (having or losing focus, or becoming visible or invisible).
try { try {
windowStage.on('windowStageEvent', (data) => { windowStage.on('windowStageEvent', (data) => {
console.info('Succeeded in enabling the listener for window stage event changes. Data: ' + let stageEventType: window.WindowStageEventType = data;
JSON.stringify(data)); switch (stageEventType) {
}); case window.WindowStageEventType.SHOWN: // Switch to the foreground.
} catch (exception) { console.info('windowStage foreground.');
console.error('Failed to enable the listener for window stage event changes. Cause:' + break;
JSON.stringify(exception)); case window.WindowStageEventType.ACTIVE: // Gain focus.
}; console.info('windowStage active.');
break;
// Set the UI loading. case window.WindowStageEventType.INACTIVE: // Lose focus.
windowStage.loadContent('pages/Index', (err, data) => { console.info('windowStage inactive.');
// ... break;
}); case window.WindowStageEventType.HIDDEN: // Switch to the background.
console.info('windowStage background.');
break;
default:
break;
}
});
} catch (exception) {
console.error('Failed to enable the listener for window stage event changes. Cause:' +
JSON.stringify(exception));
} }
// Set UI loading.
windowStage.loadContent('pages/Index', (err, data) => {
...
});
}
} }
``` ```
...@@ -82,18 +97,23 @@ import UIAbility from '@ohos.app.ability.UIAbility'; ...@@ -82,18 +97,23 @@ import UIAbility from '@ohos.app.ability.UIAbility';
import window from '@ohos.window'; import window from '@ohos.window';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
// ... windowStage: window.WindowStage;
...
onWindowStageDestroy() {
// Release UI resources. onWindowStageCreate(windowStage: window.WindowStage) {
// Unsubscribe from the WindowStage events such as having or losing focus in the onWindowStageDestroy() callback. this.windowStage = windowStage;
try { ...
windowStage.off('windowStageEvent'); }
} catch (exception) {
console.error('Failed to disable the listener for window stage event changes. Cause:' + onWindowStageDestroy() {
JSON.stringify(exception)); // Release UIresources.
}; // Unsubscribe from the WindowStage events such as having or losing focus in the onWindowStageDestroy() callback.
} try {
this.windowStage.off('windowStageEvent');
} catch (err) {
console.error(`Failed to disable the listener for window stage event changes. Code is ${err.code}, message is ${err.message}`);
};
}
} }
``` ```
...@@ -115,16 +135,16 @@ When the application is switched to the background, you can disable positioning ...@@ -115,16 +135,16 @@ When the application is switched to the background, you can disable positioning
import UIAbility from '@ohos.app.ability.UIAbility'; import UIAbility from '@ohos.app.ability.UIAbility';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
// ... ...
onForeground() { onForeground() {
// Apply for the resources required by the system or re-apply for the resources released in onBackground(). // Apply for the resources required by the system or re-apply for the resources released in onBackground().
} }
onBackground() { onBackground() {
// Release useless resources when the UI is invisible, or perform time-consuming operations in this callback, // Release useless resources when the UI is invisible, or perform time-consuming operations in this callback,
// for example, saving the status. // for example, saving the status.
} }
} }
``` ```
...@@ -137,13 +157,12 @@ The UIAbility instance is destroyed when **terminateSelf()** is called or the us ...@@ -137,13 +157,12 @@ The UIAbility instance is destroyed when **terminateSelf()** is called or the us
```ts ```ts
import UIAbility from '@ohos.app.ability.UIAbility'; import UIAbility from '@ohos.app.ability.UIAbility';
import window from '@ohos.window';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
// ... ...
onDestroy() { onDestroy() {
// Release system resources and save data. // Release system resources and save data.
} }
} }
``` ```
...@@ -11,7 +11,9 @@ The following design philosophy is behind UIAbility: ...@@ -11,7 +11,9 @@ The following design philosophy is behind UIAbility:
2. Support for multiple device types and window forms 2. Support for multiple device types and window forms
For details, see [Interpretation of the Application Model](application-model-description.md). > **NOTE**
>
> For details, see [Interpretation of the Application Model](application-model-description.md).
The UIAbility division principles and suggestions are as follows: The UIAbility division principles and suggestions are as follows:
...@@ -33,17 +35,17 @@ To enable an application to properly use a UIAbility component, declare the UIAb ...@@ -33,17 +35,17 @@ To enable an application to properly use a UIAbility component, declare the UIAb
```json ```json
{ {
"module": { "module": {
// ... ...
"abilities": [ "abilities": [
{ {
"name": "EntryAbility", // Name of the UIAbility component. "name": "EntryAbility", // Name of the UIAbility component.
"srcEnty": "./ets/entryability/EntryAbility.ts", // Code path of the UIAbility component. "srcEntry": "./ets/entryability/EntryAbility.ts", // Code path of the UIAbility component.
"description": "$string:EntryAbility_desc", // Description of the UIAbility component. "description": "$string:EntryAbility_desc", // Description of the UIAbility component.
"icon": "$media:icon", // Icon of the UIAbility component. "icon": "$media:icon", // Icon of the UIAbility component.
"label": "$string:EntryAbility_label", // Label of the UIAbility component. "label": "$string:EntryAbility_label", // Label of the UIAbility component.
"startWindowIcon": "$media:icon", // Index of the icon resource file. "startWindowIcon": "$media:icon", // Index of the icon resource file.
"startWindowBackground": "$color:start_window_background", // Index of the background color resource file. "startWindowBackground": "$color:start_window_background", // Index of the background color resource file.
// ... ...
} }
] ]
} }
......
...@@ -14,14 +14,14 @@ import UIAbility from '@ohos.app.ability.UIAbility'; ...@@ -14,14 +14,14 @@ import UIAbility from '@ohos.app.ability.UIAbility';
import window from '@ohos.window'; import window from '@ohos.window';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
onWindowStageCreate(windowStage: window.WindowStage) { onWindowStageCreate(windowStage: window.WindowStage) {
// Main window is created. Set a main page for this ability. // Main window is created. Set a main page for this ability.
windowStage.loadContent('pages/Index', (err, data) => { windowStage.loadContent('pages/Index', (err, data) => {
// ... ...
}); });
} }
// ... ...
} }
``` ```
...@@ -40,15 +40,14 @@ The UIAbility class has its own context, which is an instance of the [UIAbilityC ...@@ -40,15 +40,14 @@ The UIAbility class has its own context, which is an instance of the [UIAbilityC
import UIAbility from '@ohos.app.ability.UIAbility'; import UIAbility from '@ohos.app.ability.UIAbility';
export default class EntryAbility extends UIAbility { export default class EntryAbility extends UIAbility {
onCreate(want, launchParam) { onCreate(want, launchParam) {
// Obtain the context of the UIAbility instance. // Obtain the context of the UIAbility instance.
let context = this.context; let context = this.context;
...
// ... }
}
} }
``` ```
- Import the context module and define the **context** variable in the component. - Import the context module and define the **context** variable in the component.
```ts ```ts
...@@ -68,7 +67,7 @@ The UIAbility class has its own context, which is an instance of the [UIAbilityC ...@@ -68,7 +67,7 @@ The UIAbility class has its own context, which is an instance of the [UIAbilityC
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
...@@ -93,7 +92,7 @@ The UIAbility class has its own context, which is an instance of the [UIAbilityC ...@@ -93,7 +92,7 @@ The UIAbility class has its own context, which is an instance of the [UIAbilityC
// Page display. // Page display.
build() { build() {
// ... ...
} }
} }
``` ```
...@@ -3,47 +3,49 @@ ...@@ -3,47 +3,49 @@
## Definition and Usage of Want ## Definition and Usage of Want
[Want](../reference/apis/js-apis-app-ability-want.md) is used as the carrier to transfer information between application components. It is used as a parameter of **startAbility()** to specify the startup target and information that needs to be carried during startup, for example, **bundleName** and **abilityName**, which respectively indicate the bundle name of the target ability and the ability name in the bundle. For example, when UIAbilityA starts UIAbilityB and needs to transfer some data to UIAbilityB, it can use Want to transfer the data. [Want](../reference/apis/js-apis-app-ability-want.md) is an object that transfers information between application components. It is often used as a parameter of [startAbility()](../reference/apis/js-apis-inner-application-uiAbilityContext.md#uiabilitycontextstartability). For example, when UIAbilityA needs to start UIAbilityB and transfer some data to UIAbilityB, it can use the **want** parameter in **startAbility()** to transfer the data.
**Figure 1** Want usage **Figure 1** Want usage
![usage-of-want](figures/usage-of-want.png) ![usage-of-want](figures/usage-of-want.png)
## Types of Want ## Types of Want
- **Explicit Want**: A type of Want with **abilityName** and **bundleName** specified when starting an ability. - **Explicit Want**: If **abilityName** and **bundleName** are specified in the **want** parameter when starting an an application component, explicit Want is used.
When there is an explicit object to process the request, the target ability can be started by specifying the bundle name and ability name in Want. Explicit Want is usually used to start a known ability.
Explicit Want is usually used to start a known target application component in the same application. The target application component is started by specifying **bundleName** of the application where the target application component is located and **abilityName** in the **Want** object. When there is an explicit object to process the request, explicit Want is a simple and effective way to start the target application component.
```ts ```ts
let wantInfo = { let wantInfo = {
deviceId: '', // An empty deviceId indicates the local device. deviceId: '', // An empty deviceId indicates the local device.
bundleName: 'com.example.myapplication', bundleName: 'com.example.myapplication',
abilityName: 'FuncAbility', abilityName: 'FuncAbility',
} }
``` ```
- **Implicit Want**: A type of Want with **abilityName** unspecified when starting the ability. - **Implicit Want**: If **abilityName** is not specified in the **want** parameter when starting the an application component, implicit Want is used.
Implicit Want can be used when the object used to process the request is unclear and the current application wants to use a capability (defined by the [skills tag](../quick-start/module-configuration-file.md#skills)) provided by another application. For example, you can use implicit Want to describe a request for opening a link, since you do not care which application is used to open the link. The system matches all applications that support the request.
Implicit Want can be used when the object used to process the request is unclear and the current application wants to use a capability (defined by the [skills tag](../quick-start/module-configuration-file.md#skills)) provided by another application. The system matches all applications that declare to support the capability. For example, for a link open request, the system matches all applications that support the request and provides the available ones for users to select.
```ts ```ts
let wantInfo = { let wantInfo = {
// Uncomment the line below if you want to implicitly query data only in the specific bundle. // Uncomment the line below if you want to implicitly query data only in the specific bundle.
// bundleName: 'com.example.myapplication', // bundleName: 'com.example.myapplication',
action: 'ohos.want.action.search', action: 'ohos.want.action.search',
// entities can be omitted. // entities can be omitted.
entities: [ 'entity.system.browsable' ], entities: [ 'entity.system.browsable' ],
uri: 'https://www.test.com:8080/query/student', uri: 'https://www.test.com:8080/query/student',
type: 'text/plain', type: 'text/plain',
}; };
``` ```
> **NOTE** > **NOTE**
> - Depending on the ability matching result, the following cases may be possible when you attempt to use implicit Want to start the ability. > - Depending on the application component matching result, the following cases may be possible when you attempt to use implicit Want to start the application component.
> - No ability is matched. The startup fails. > - No application component is matched. The startup fails.
> - An ability that meets the conditions is matched. That ability is started. > - An application component that meets the conditions is matched. That application component is started.
> - Multiple abilities that meet the conditions are matched. A dialog box is displayed for users to select one of them. > - Multiple application components that meet the conditions are matched. A dialog box is displayed for users to select one of them.
> >
> - If the **want** parameter passed does not contain **abilityName** or **bundleName**, the ServiceExtensionAbility components of all applications cannot be started through implicit Want. > - If the **want** parameter passed does not contain **abilityName** or **bundleName**, the ServiceExtensionAbility components of all applications cannot be started through implicit Want.
> >
......
...@@ -20,7 +20,7 @@ Before you get started, it would be helpful if you have a basic understanding of ...@@ -20,7 +20,7 @@ Before you get started, it would be helpful if you have a basic understanding of
Figure 1 shows the working principles of the widget framework. Figure 1 shows the working principles of the widget framework.
**Figure 1** Widget framework working principles in the FA model **Figure 1** Widget framework working principles in the FA model
![form-extension](figures/form-extension.png) ![form-extension](figures/form-extension.png)
The widget host consists of the following modules: The widget host consists of the following modules:
...@@ -122,48 +122,48 @@ To create a widget in the FA model, implement the widget lifecycle callbacks. Ge ...@@ -122,48 +122,48 @@ To create a widget in the FA model, implement the widget lifecycle callbacks. Ge
```ts ```ts
export default { export default {
onCreate(want) { onCreate(want) {
console.info('FormAbility onCreate'); console.info('FormAbility onCreate');
// Called when the widget is created. The widget provider should return the widget data binding class. // Called when the widget is created. The widget provider should return the widget data binding class.
let obj = { let obj = {
"title": "titleOnCreate", "title": "titleOnCreate",
"detail": "detailOnCreate" "detail": "detailOnCreate"
}; };
let formData = formBindingData.createFormBindingData(obj); let formData = formBindingData.createFormBindingData(obj);
return formData; return formData;
}, },
onCastToNormal(formId) { onCastToNormal(formId) {
// Called when the widget host converts the temporary widget into a normal one. The widget provider should do something to respond to the conversion. // Called when the widget host converts the temporary widget into a normal one. The widget provider should do something to respond to the conversion.
console.info('FormAbility onCastToNormal'); console.info('FormAbility onCastToNormal');
}, },
onUpdate(formId) { onUpdate(formId) {
// Override this method to support scheduled updates, periodic updates, or updates requested by the widget host. // Override this method to support scheduled updates, periodic updates, or updates requested by the widget host.
console.info('FormAbility onUpdate'); console.info('FormAbility onUpdate');
let obj = { let obj = {
"title": "titleOnUpdate", "title": "titleOnUpdate",
"detail": "detailOnUpdate" "detail": "detailOnUpdate"
}; };
let formData = formBindingData.createFormBindingData(obj); let formData = formBindingData.createFormBindingData(obj);
formProvider.updateForm(formId, formData).catch((error) => { formProvider.updateForm(formId, formData).catch((error) => {
console.info('FormAbility updateForm, error:' + JSON.stringify(error)); console.info('FormAbility updateForm, error:' + JSON.stringify(error));
}); });
}, },
onVisibilityChange(newStatus) { onVisibilityChange(newStatus) {
// Called when the widget host initiates an event about visibility changes. The widget provider should do something to respond to the notification. This callback takes effect only for system applications. // Called when the widget host initiates an event about visibility changes. The widget provider should do something to respond to the notification. This callback takes effect only for system applications.
console.info('FormAbility onVisibilityChange'); console.info('FormAbility onVisibilityChange');
}, },
onEvent(formId, message) { onEvent(formId, message) {
// If the widget supports event triggering, override this method and implement the trigger. // If the widget supports event triggering, override this method and implement the trigger.
console.info('FormAbility onEvent'); console.info('FormAbility onEvent');
}, },
onDestroy(formId) { onDestroy(formId) {
// Delete widget data. // Delete widget data.
console.info('FormAbility onDestroy'); console.info('FormAbility onDestroy');
}, },
onAcquireFormState(want) { onAcquireFormState(want) {
console.info('FormAbility onAcquireFormState'); console.info('FormAbility onAcquireFormState');
return formInfo.FormState.READY; return formInfo.FormState.READY;
}, },
} }
``` ```
...@@ -188,15 +188,15 @@ The widget configuration file is named **config.json**. Find the **config.json** ...@@ -188,15 +188,15 @@ The widget configuration file is named **config.json**. Find the **config.json**
```json ```json
"js": [{ "js": [{
"name": "widget", "name": "widget",
"pages": ["pages/index/index"], "pages": ["pages/index/index"],
"window": { "window": {
"designWidth": 720, "designWidth": 720,
"autoDesignWidth": true "autoDesignWidth": true
}, },
"type": "form" "type": "form"
}] }]
``` ```
- The **abilities** module in the **config.json** file corresponds to **FormAbility** of the widget. The internal structure is described as follows: - The **abilities** module in the **config.json** file corresponds to **FormAbility** of the widget. The internal structure is described as follows:
...@@ -232,7 +232,7 @@ The widget configuration file is named **config.json**. Find the **config.json** ...@@ -232,7 +232,7 @@ The widget configuration file is named **config.json**. Find the **config.json**
"type": "service", "type": "service",
"srcLanguage": "ets", "srcLanguage": "ets",
"formsEnabled": true, "formsEnabled": true,
"formConfigAbility": "ability://com.example.entry.MainAbility", "formConfigAbility": "ability://com.example.entry.EntryAbility",
"forms": [{ "forms": [{
"colorMode": "auto", "colorMode": "auto",
"defaultDimension": "2*2", "defaultDimension": "2*2",
...@@ -275,7 +275,7 @@ async function storeFormInfo(formId: string, formName: string, tempFlag: boolean ...@@ -275,7 +275,7 @@ async function storeFormInfo(formId: string, formName: string, tempFlag: boolean
} }
} }
// ... ...
onCreate(want) { onCreate(want) {
console.info('FormAbility onCreate'); console.info('FormAbility onCreate');
...@@ -293,7 +293,7 @@ async function storeFormInfo(formId: string, formName: string, tempFlag: boolean ...@@ -293,7 +293,7 @@ async function storeFormInfo(formId: string, formName: string, tempFlag: boolean
let formData = formBindingData.createFormBindingData(obj); let formData = formBindingData.createFormBindingData(obj);
return formData; return formData;
} }
// ... ...
``` ```
You should override **onDestroy** to implement widget data deletion. You should override **onDestroy** to implement widget data deletion.
...@@ -313,14 +313,14 @@ async function deleteFormInfo(formId: string) { ...@@ -313,14 +313,14 @@ async function deleteFormInfo(formId: string) {
} }
} }
// ... ...
onDestroy(formId) { onDestroy(formId) {
console.info('FormAbility onDestroy'); console.info('FormAbility onDestroy');
// Delete the persistent widget instance data. // Delete the persistent widget instance data.
// Implement this API based on project requirements. // Implement this API based on project requirements.
deleteFormInfo(formId); deleteFormInfo(formId);
} }
// ... ...
``` ```
For details about how to implement persistent data storage, see [Application Data Persistence Overview](../database/app-data-persistence-overview.md). For details about how to implement persistent data storage, see [Application Data Persistence Overview](../database/app-data-persistence-overview.md).
...@@ -434,7 +434,7 @@ You can use the web-like paradigm (HML+CSS+JSON) to develop JS widget pages. Thi ...@@ -434,7 +434,7 @@ You can use the web-like paradigm (HML+CSS+JSON) to develop JS widget pages. Thi
"actions": { "actions": {
"routerEvent": { "routerEvent": {
"action": "router", "action": "router",
"abilityName": "com.example.entry.MainAbility", "abilityName": "com.example.entry.EntryAbility",
"params": { "params": {
"message": "add detail" "message": "add detail"
} }
...@@ -452,8 +452,8 @@ You can set router and message events for components on a widget. The router eve ...@@ -452,8 +452,8 @@ You can set router and message events for components on a widget. The router eve
2. Set the router event. 2. Set the router event.
- **action**: **"router"**, which indicates a router event. - **action**: **"router"**, which indicates a router event.
- **abilityName**: name of the ability to redirect to (PageAbility component in the FA model and UIAbility component in the stage model). For example, the default UIAbility name created by DevEco Studio in the FA model is com.example.entry.MainAbility. - **abilityName**: name of the ability to redirect to (PageAbility component in the FA model and UIAbility component in the stage model). For example, the default UIAbility name created by DevEco Studio in the FA model is com.example.entry.EntryAbility.
- **params**: custom parameters passed to the target ability. Set them as required. The value can be obtained from **parameters** in **want** used for starting the target ability. For example, in the lifecycle function **onCreate** of the MainAbility in the FA model, **featureAbility.getWant()** can be used to obtain **want** and its **parameters** field. - **params**: custom parameters passed to the target ability. Set them as required. The value can be obtained from **parameters** in **want** used for starting the target ability. For example, in the lifecycle function **onCreate** of the EntryAbility in the FA model, **featureAbility.getWant()** can be used to obtain **want** and its **parameters** field.
3. Set the message event. 3. Set the message event.
- **action**: **"message"**, which indicates a message event. - **action**: **"message"**, which indicates a message event.
...@@ -529,7 +529,7 @@ The following is an example: ...@@ -529,7 +529,7 @@ The following is an example:
"actions": { "actions": {
"routerEvent": { "routerEvent": {
"action": "router", "action": "router",
"abilityName": "com.example.entry.MainAbility", "abilityName": "com.example.entry.EntryAbility",
"params": { "params": {
"message": "add detail" "message": "add detail"
} }
......
...@@ -11,7 +11,7 @@ Widget switching involves the following parts: ...@@ -11,7 +11,7 @@ Widget switching involves the following parts:
| Configuration Item | FA Model | Stage Model | | Configuration Item | FA Model | Stage Model |
| ---------------- | ------------------------------------------- | ------------------------------------------------------------ | | ---------------- | ------------------------------------------- | ------------------------------------------------------------ |
| Configuration item location | **formAbility** and **forms** are in the **config.json** file.| **extensionAbilities** (configuration for **formExtensionAbility**) is in the **module.json5** file in the level-1 directory, and **forms** (configuration for **forms** contained in **formExtensionAbility**) is in the **form_config.json** file in the level-2 directory.| | Configuration item location | **formAbility** and **forms** are in the **config.json** file.| **extensionAbilities** (configuration for **formExtensionAbility**) is in the **module.json5** file in the level-1 directory, and **forms** (configuration for **forms** contained in **formExtensionAbility**) is in the **form_config.json** file in the level-2 directory.|
| Widget code path | Specified by **srcPath**, without the file name. | Specified by **srcEnty**, with the file name. | | Widget code path | Specified by **srcPath**, without the file name. | Specified by **srcEntry**, with the file name. |
| Programming language | **srcLanguage** can be set to **js** or **ets**. | This configuration item is unavailable. Only ets is supported. | | Programming language | **srcLanguage** can be set to **js** or **ets**. | This configuration item is unavailable. Only ets is supported. |
| Whether to enable widgets | formsEnabled | This configuration item is unavailable. The setting of **type** set to **form** means that the widgets are enabled. | | Whether to enable widgets | formsEnabled | This configuration item is unavailable. The setting of **type** set to **form** means that the widgets are enabled. |
| Ability type | type: service | type: form | | Ability type | type: service | type: form |
...@@ -32,7 +32,7 @@ Figure 2 Widget configuration differences ...@@ -32,7 +32,7 @@ Figure 2 Widget configuration differences
| Item| FA Model| Stage Model| | Item| FA Model| Stage Model|
| -------- | -------- | -------- | | -------- | -------- | -------- |
| Entry file| **form.ts** in the directory pointed to by **srcPath**| File pointed to by **srcEnty**| | Entry file| **form.ts** in the directory pointed to by **srcPath**| File pointed to by **srcEntry**|
| Lifecycle| export default| import FormExtension from '\@ohos.app.form.FormExtensionAbility';<br>export default class FormAbility extends FormExtension| | Lifecycle| export default| import FormExtension from '\@ohos.app.form.FormExtensionAbility';<br>export default class FormAbility extends FormExtension|
......
...@@ -43,7 +43,7 @@ To implement an embedded application, manually create a WindowExtensionAbility i ...@@ -43,7 +43,7 @@ To implement an embedded application, manually create a WindowExtensionAbility i
onWindowReady(window) { onWindowReady(window) {
window.loadContent('WindowExtAbility/pages/index1').then(() => { window.loadContent('WindowExtAbility/pages/index1').then(() => {
window.getProperties().then((pro) => { window.getProperties().then((pro) => {
console.log("WindowExtension " + JSON.stringify(pro)); console.info("WindowExtension " + JSON.stringify(pro));
}) })
window.show(); window.show();
}) })
...@@ -59,7 +59,7 @@ To implement an embedded application, manually create a WindowExtensionAbility i ...@@ -59,7 +59,7 @@ To implement an embedded application, manually create a WindowExtensionAbility i
} }
``` ```
4. Register the WindowExtensionAbility in the [module.json5 file](../quick-start/module-configuration-file.md) corresponding to the **Module** project. Set **type** to **"window"** and **srcEnty** to the code path of the ExtensionAbility component. 4. Register the WindowExtensionAbility in the [module.json5 file](../quick-start/module-configuration-file.md) corresponding to the **Module** project. Set **type** to **"window"** and **srcEntry** to the code path of the ExtensionAbility component.
```json ```json
{ {
...@@ -67,7 +67,7 @@ To implement an embedded application, manually create a WindowExtensionAbility i ...@@ -67,7 +67,7 @@ To implement an embedded application, manually create a WindowExtensionAbility i
"extensionAbilities": [ "extensionAbilities": [
{ {
"name": "WindowExtAbility", "name": "WindowExtAbility",
"srcEnty": "./ets/WindowExtAbility/WindowExtAbility.ts", "srcEntry": "./ets/WindowExtAbility/WindowExtAbility.ts",
"icon": "$media:icon", "icon": "$media:icon",
"description": "WindowExtension", "description": "WindowExtension",
"type": "window", "type": "window",
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册