未验证 提交 4f992784 编写于 作者: O openharmony_ci 提交者: Gitee

!17667 翻译完成:16735+17296+17418+17488 ability-deprecated文件夹更新

Merge pull request !17667 from wusongqing/TR16735
...@@ -116,7 +116,7 @@ Example URIs: ...@@ -116,7 +116,7 @@ Example URIs:
| "name" | Ability name, corresponding to the **Data** class name derived from **Ability**. | | "name" | Ability name, corresponding to the **Data** class name derived from **Ability**. |
| "type" | Ability type, which is **Data** for a Data ability. | | "type" | Ability type, which is **Data** for a Data ability. |
| "uri" | URI used for communication. | | "uri" | URI used for communication. |
| "visible" | Whether the Data ability is visible to other applications. When this parameter is set to **true**, the Data ability can communicate with other applications.| | "exported" | Whether the Data ability is visible to other applications. When this parameter is set to **true**, the Data ability can communicate with other applications.|
**config.json configuration example** **config.json configuration example**
...@@ -128,7 +128,7 @@ Example URIs: ...@@ -128,7 +128,7 @@ Example URIs:
"srcLanguage": "ets", "srcLanguage": "ets",
"description": "$string:description_dataability", "description": "$string:description_dataability",
"type": "data", "type": "data",
"visible": true, "exported": true,
"uri": "dataability://ohos.samples.etsdataability.DataAbility" "uri": "dataability://ohos.samples.etsdataability.DataAbility"
}] }]
``` ```
...@@ -154,7 +154,7 @@ The basic dependency packages include: ...@@ -154,7 +154,7 @@ The basic dependency packages include:
import featureAbility from '@ohos.ability.featureAbility' import featureAbility from '@ohos.ability.featureAbility'
import ohos_data_ability from '@ohos.data.dataAbility' import ohos_data_ability from '@ohos.data.dataAbility'
import ohos_data_rdb from '@ohos.data.rdb' import ohos_data_rdb from '@ohos.data.rdb'
var urivar = "dataability:///com.ix.DataAbility" var urivar = "dataability:///com.ix.DataAbility"
var DAHelper = featureAbility.acquireDataAbilityHelper( var DAHelper = featureAbility.acquireDataAbilityHelper(
urivar urivar
......
...@@ -25,7 +25,7 @@ Carry out the following operations to develop the widget provider based on the [ ...@@ -25,7 +25,7 @@ Carry out the following operations to develop the widget provider based on the [
1. Implement lifecycle callbacks by using the **LifecycleForm** APIs. 1. Implement lifecycle callbacks by using the **LifecycleForm** APIs.
2. Create a **FormBindingData** instance. 2. Create a **FormBindingData** instance.
3. Update a widget by using the **FormProvider** APIs. 3. Update a widget by using the **FormProvider** APIs.
4. Develop the widget UI pages. 4. Develop the widget UI page.
## Available APIs ## Available APIs
...@@ -231,7 +231,7 @@ You should override **onDestroy** to implement widget data deletion. ...@@ -231,7 +231,7 @@ You should override **onDestroy** to implement widget data deletion.
} }
``` ```
For details about how to implement persistent data storage, see [Lightweight Data Store Development](../database/database-preference-guidelines.md). For details about how to implement persistent data storage, see [Data Persistence by User Preferences](../database/data-persistence-by-preferences.md).
The **Want** object passed in by the widget host to the widget provider contains a flag that specifies whether the requested widget is normal or temporary. The **Want** object passed in by the widget host to the widget provider contains a flag that specifies whether the requested widget is normal or temporary.
...@@ -355,7 +355,7 @@ You can set router and message events for components on a widget. The router eve ...@@ -355,7 +355,7 @@ You can set router and message events for components on a widget. The router eve
1. Set the **onclick** field in the HML file to **routerEvent** or **messageEvent**, depending on the **actions** settings in the JSON file. 1. Set the **onclick** field in the HML file to **routerEvent** or **messageEvent**, depending on the **actions** settings in the JSON file.
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**: target ability name, for example, **com.example.entry.MainAbility**, which is the default UIAbility name in DevEco Studio for the FA model. - **abilityName**: target ability name, for example, **com.example.entry.MainAbility**, which is the default main ability name in DevEco Studio for the FA model.
- **params**: custom parameters of 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 main ability in the FA model, **featureAbility.getWant()** can be used to obtain **want** and its **parameters** field. - **params**: custom parameters of 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 main ability 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.
......
...@@ -47,7 +47,7 @@ You can specify the launch type by setting **launchType** in the **config.json** ...@@ -47,7 +47,7 @@ You can specify the launch type by setting **launchType** in the **config.json**
| Launch Type | Description |Description | | Launch Type | Description |Description |
| ----------- | ------- |---------------- | | ----------- | ------- |---------------- |
| standard | Multi-instance | A new instance is started each time an ability starts.| | standard | Multi-instance | A new instance is started each time an ability starts.|
| singleton | Singleton | The ability has only one instance in the system. If an instance already exists when an ability is started, that instance is reused.| | singleton | Singleton | The ability has only one instance in the system. If an instance already exists when an ability is started, that instance is reused.|
By default, **singleton** is used. By default, **singleton** is used.
......
...@@ -48,96 +48,89 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar ...@@ -48,96 +48,89 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar
} }
``` ```
- Configure the application startup type. - Configure the application startup type.
If **launchType** is set to **standard** in the **module.json5** file, the application is of the multi-instance launch type. During ability continuation, regardless of whether the application is already open, the target starts the application and restores the UI page. If **launchType** is set to **singleton**, the application is of the singleton launch type. If the application is already open, the target clears the existing page stack and restores the UI page. For more information, see "Launch Type" in [Ability Development](./stage-ability.md). If **launchType** is set to **multiton** in the **module.json5** file, the application is of the multi-instance launch type. During ability continuation, regardless of whether the application is already open, the target starts the application and restores the UI page. If **launchType** is set to **singleton**, the application is of the singleton launch type. If the application is already open, the target clears the existing page stack and restores the UI page. For more information, see "Launch Type" in [Ability Development](./stage-ability.md).
Configure a multi-instance application as follows:
```javascript
{
"module": {
"abilities": [
{
"launchType": "multiton"
}
]
}
}
```
Configure a singleton application as follows or retain the default settings of **launchType**:
```javascript
{
"module": {
"abilities": [
{
"launchType": "singleton"
}
]
}
}
```
- Apply for the distributed permissions.
Configure a multi-instance application as follows: Declare the **DISTRIBUTED_DATASYNC** permission in the **module.json5** file for the application.
```javascript ```javascript
{ "requestPermissions": [
"module": { {
"abilities": [ "name": "ohos.permission.DISTRIBUTED_DATASYNC"
{ },
"launchType": "standard" ```
}
]
}
}
```
Configure a singleton application as follows or retain the default settings of **launchType**: This permission must be granted by the user in a dialog box when the application is started for the first time. To enable the application to display a dialog box to ask for the permission, add the following code to **onWindowStageCreate** of the **Ability** class:
```javascript ```javascript
{ requestPermissions = async () => {
"module": { let permissions: Array<string> = [
"abilities": [ "ohos.permission.DISTRIBUTED_DATASYNC"
{ ];
"launchType": "singleton" let needGrantPermission = false
let accessManger = accessControl.createAtManager()
Logger.info("app permission get bundle info")
let bundleInfo = await bundle.getApplicationInfo(BUNDLE_NAME, 0, 100)
Logger.info(`app permission query permission ${bundleInfo.accessTokenId.toString()}`)
for (const permission of permissions) {
Logger.info(`app permission query grant status ${permission}`)
try {
let grantStatus = await accessManger.verifyAccessToken(bundleInfo.accessTokenId, permission)
if (grantStatus === PERMISSION_REJECT) {
needGrantPermission = true
break;
}
} catch (err) {
Logger.error(`app permission query grant status error ${permission} ${JSON.stringify(err)}`)
needGrantPermission = true
break;
}
}
if (needGrantPermission) {
Logger.info("app permission needGrantPermission")
try {
await accessManger.requestPermissionsFromUser(this.context, permissions)
} catch (err) {
Logger.error(`app permission ${JSON.stringify(err)}`)
}
} else {
Logger.info("app permission already granted")
}
} }
] ```
}
}
```
- Apply for the distributed permissions.
Declare the **DISTRIBUTED_DATASYNC** permission in the **module.json5** file for the application.
```javascript
"requestPermissions": [
{
"name": "ohos.permission.DISTRIBUTED_DATASYNC"
},
```
This permission must be granted by the user in a dialog box when the application is started for the first time. To enable the application to display a dialog box to ask for the permission, add the following code to **onWindowStageCreate** of the **Ability** class:
```javascript
requestPermissions = async () => {
let permissions: Array<string> = [
"ohos.permission.DISTRIBUTED_DATASYNC"
];
let needGrantPermission = false
let accessManger = accessControl.createAtManager()
Logger.info("app permission get bundle info")
let bundleInfo = await bundle.getApplicationInfo(BUNDLE_NAME, 0, 100)
Logger.info(`app permission query permission ${bundleInfo.accessTokenId.toString()}`)
for (const permission of permissions) {
Logger.info(`app permission query grant status ${permission}`)
try {
let grantStatus = await accessManger.verifyAccessToken(bundleInfo.accessTokenId, permission)
if (grantStatus === PERMISSION_REJECT) {
needGrantPermission = true
break;
}
} catch (err) {
Logger.error(`app permission query grant status error ${permission} ${JSON.stringify(err)}`)
needGrantPermission = true
break;
}
}
if (needGrantPermission) {
Logger.info("app permission needGrantPermission")
try {
await accessManger.requestPermissionsFromUser(this.context, permissions)
} catch (err) {
Logger.error(`app permission ${JSON.stringify(err)}`)
}
} else {
Logger.info("app permission already granted")
}
}
```
2. Implement the **onContinue()** API. 2. Implement the **onContinue()** API.
...@@ -155,7 +148,7 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar ...@@ -155,7 +148,7 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar
You can obtain the target device ID (identified by the key **targetDevice**) and the version number (identified by the key **version**) of the application installed on the target device from the **wantParam** parameter of this API. The version number can be used for compatibility check. If the current application version is incompatible with that on the target device, **OnContinueResult.MISMATCH** can be returned to reject the continuation request. You can obtain the target device ID (identified by the key **targetDevice**) and the version number (identified by the key **version**) of the application installed on the target device from the **wantParam** parameter of this API. The version number can be used for compatibility check. If the current application version is incompatible with that on the target device, **OnContinueResult.MISMATCH** can be returned to reject the continuation request.
Example Example:
```javascript ```javascript
onContinue(wantParam : {[key: string]: any}) { onContinue(wantParam : {[key: string]: any}) {
...@@ -168,8 +161,6 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar ...@@ -168,8 +161,6 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar
} }
``` ```
3. Implement the continuation logic in the **onCreate()** or **onNewWant()** API. 3. Implement the continuation logic in the **onCreate()** or **onNewWant()** API.
The **onCreate()** API is called by the target. When the ability is started on the target device, this API is called to instruct the application to synchronize the memory data and UI component state, and triggers page restoration after the synchronization is complete. If the continuation logic is not implemented, the ability will be started in common startup mode and the page cannot be restored. The **onCreate()** API is called by the target. When the ability is started on the target device, this API is called to instruct the application to synchronize the memory data and UI component state, and triggers page restoration after the synchronization is complete. If the continuation logic is not implemented, the ability will be started in common startup mode and the page cannot be restored.
...@@ -178,11 +169,9 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar ...@@ -178,11 +169,9 @@ The code snippets provided below are all from [Sample](https://gitee.com/openhar
After data restore is complete, call **restoreWindowStage** to trigger page restoration. After data restore is complete, call **restoreWindowStage** to trigger page restoration.
You can also use **want.parameters.version** in the **want** parameter to obtain the application version number of the initiator. You can also use **want.parameters.version** in the **want** parameter to obtain the application version number of the initiator.
Example Example:
```javascript ```javascript
import Ability from '@ohos.application.Ability'; import Ability from '@ohos.application.Ability';
...@@ -211,9 +200,9 @@ For a singleton ability, use **onNewWant()** to achieve the same implementation. ...@@ -211,9 +200,9 @@ For a singleton ability, use **onNewWant()** to achieve the same implementation.
Use distributed objects. Use distributed objects.
Distributed objects allow cross-device data synchronization like local variables. For two devices that form a Super Device, when data in the distributed data object of an application is added, deleted, or modified on a device, the data for the same application is also updated on the other device. Both devices can listen for the data changes and online and offline states of the other. For details, see [Distributed Data Object Development](../database/database-distributedobject-guidelines.md). Distributed objects allow cross-device data synchronization like local variables. For two devices that form a Super Device, when data in the distributed data object of an application is added, deleted, or modified on a device, the data for the same application is also updated on the other device. Both devices can listen for the data changes and online and offline states of the other. For details, see [Sharing Distributed Data Objects](../database/data-sync-of-distributed-data-object.md).
In the ability continuation scenario, the distributed data object is used to synchronize the memory data from the local device to the target device. In the ability continuation scenario, the distributed data object is used to synchronize the memory data from the local device to the target device. For details, see [Distributed Data Object Development](../database/database-distributedobject-guidelines.md).
- In **onContinue()**, the initiator saves the data to be migrated to the distributed object, calls the **save()** API to save the data and synchronize the data to the target device, sets the session ID, and sends the session ID to the target device through **wantParam**. - In **onContinue()**, the initiator saves the data to be migrated to the distributed object, calls the **save()** API to save the data and synchronize the data to the target device, sets the session ID, and sends the session ID to the target device through **wantParam**.
...@@ -249,8 +238,6 @@ In the ability continuation scenario, the distributed data object is used to syn ...@@ -249,8 +238,6 @@ In the ability continuation scenario, the distributed data object is used to syn
}); });
``` ```
- The target device obtains the session ID from **onCreate()**, creates a distributed object, and associates the distributed object with the session ID. In this way, the distributed object can be synchronized. Before calling **restoreWindowStage**, ensure that all distributed objects required for continuation have been associated. - The target device obtains the session ID from **onCreate()**, creates a distributed object, and associates the distributed object with the session ID. In this way, the distributed object can be synchronized. Before calling **restoreWindowStage**, ensure that all distributed objects required for continuation have been associated.
```javascript ```javascript
...@@ -266,11 +253,11 @@ In the ability continuation scenario, the distributed data object is used to syn ...@@ -266,11 +253,11 @@ In the ability continuation scenario, the distributed data object is used to syn
onCreate(want, launchParam) { onCreate(want, launchParam) {
Logger.info(`MainAbility onCreate ${AbilityConstant.LaunchReason.CONTINUATION}`) Logger.info(`MainAbility onCreate ${AbilityConstant.LaunchReason.CONTINUATION}`)
if (launchParam.launchReason == AbilityConstant.LaunchReason.CONTINUATION) { if (launchParam.launchReason == AbilityConstant.LaunchReason.CONTINUATION) {
// Obtain the session ID of the distributed data object from the want parameter. // Obtain the session ID of the distributed data object from the want parameter.
this.sessionId = want.parameters.session this.sessionId = want.parameters.session
Logger.info(`onCreate for continuation sessionId: ${this.sessionId}`) Logger.info(`onCreate for continuation sessionId: ${this.sessionId}`)
// Before fetching data from the remote device, reset g_object.data to undefined. // Before fetching data from the remote device, reset g_object.data to undefined.
g_object.data = undefined; g_object.data = undefined;
// Set the session ID, so the target will fetch data from the remote device. // Set the session ID, so the target will fetch data from the remote device.
g_object.setSessionId(this.sessionId); g_object.setSessionId(this.sessionId);
...@@ -284,8 +271,6 @@ In the ability continuation scenario, the distributed data object is used to syn ...@@ -284,8 +271,6 @@ In the ability continuation scenario, the distributed data object is used to syn
} }
``` ```
### More Information ### More Information
1. Timeout 1. Timeout
...@@ -295,15 +280,11 @@ In the ability continuation scenario, the distributed data object is used to syn ...@@ -295,15 +280,11 @@ In the ability continuation scenario, the distributed data object is used to syn
2. By default, the system supports page stack information migration, which means that the page stack of the initiator will be automatically migrated to the target device. No adaptation is required. 2. By default, the system supports page stack information migration, which means that the page stack of the initiator will be automatically migrated to the target device. No adaptation is required.
### Restrictions ### Restrictions
1. The continuation must be performed between the same ability, which means the same bundle name, module name, and ability name. For details, see [Application Package Structure Configuration File](../quick-start/module-configuration-file.md). 1. The continuation must be performed between the same ability, which means the same bundle name, module name, and ability name. For details, see [Application Package Structure Configuration File](../quick-start/module-configuration-file.md).
2. Currently, the application can only implement the continuation capability. The continuation action must be initiated by the system. 2. Currently, the application can only implement the continuation capability. The continuation action must be initiated by the system.
### Best Practice ### Best Practice
For better user experience, you are advised to use the **wantParam** parameter to transmit data smaller than 100 KB and use distributed objects to transmit data larger than 100 KB. For better user experience, you are advised to use the **wantParam** parameter to transmit data smaller than 100 KB and use distributed objects to transmit data larger than 100 KB.
...@@ -12,7 +12,7 @@ An ability can be launched in the **standard**, **singleton**, or **specified** ...@@ -12,7 +12,7 @@ An ability can be launched in the **standard**, **singleton**, or **specified**
| Launch Type | Description |Action | | Launch Type | Description |Action |
| ----------- | ------- |---------------- | | ----------- | ------- |---------------- |
| standard | Standard mode | A new instance is started each time an ability starts.| | multiton | Multi-instance mode| A new instance is started each time an ability starts.|
| singleton | Singleton mode | The ability has only one instance in the system. If an instance already exists when an ability is started, that instance is reused.| | singleton | Singleton mode | The ability has only one instance in the system. If an instance already exists when an ability is started, that instance is reused.|
| specified | Instance-specific| The internal service of an ability determines whether to create multiple instances during running.| | specified | Instance-specific| The internal service of an ability determines whether to create multiple instances during running.|
...@@ -71,7 +71,7 @@ To create Page abilities for an application in the stage model, you must impleme ...@@ -71,7 +71,7 @@ To create Page abilities for an application in the stage model, you must impleme
```js ```js
import Ability from '@ohos.application.Ability' import Ability from '@ohos.application.Ability'
``` ```
4. Implement the lifecycle callbacks of the **UIAbility** class. The default relative path generated by the APIs is **entry\src\main\ets\MainAbility\MainAbility.ts**. 4. Implement the lifecycle callbacks of the **UIAbility** class. The default relative path generated by the APIs is **entry\src\main\ets\entryability\EntryAbility.ts**.
In the **onWindowStageCreate(windowStage)** API, use **loadContent** to set the application page to be loaded. For details about how to use the **Window** APIs, see [Window Development](../windowmanager/application-window-stage.md). In the **onWindowStageCreate(windowStage)** API, use **loadContent** to set the application page to be loaded. For details about how to use the **Window** APIs, see [Window Development](../windowmanager/application-window-stage.md).
```ts ```ts
...@@ -79,29 +79,29 @@ To create Page abilities for an application in the stage model, you must impleme ...@@ -79,29 +79,29 @@ To create Page abilities for an application in the stage model, you must impleme
onCreate(want, launchParam) { onCreate(want, launchParam) {
console.log("MainAbility onCreate") console.log("MainAbility onCreate")
} }
onDestroy() { onDestroy() {
console.log("MainAbility onDestroy") console.log("MainAbility onDestroy")
} }
onWindowStageCreate(windowStage) { onWindowStageCreate(windowStage) {
console.log("MainAbility onWindowStageCreate") console.log("MainAbility onWindowStageCreate")
windowStage.loadContent("pages/index").then(() => { windowStage.loadContent("pages/index").then(() => {
console.log("MainAbility load content succeed") console.log("MainAbility load content succeed")
}).catch((error) => { }).catch((error) => {
console.error("MainAbility load content failed with error: " + JSON.stringify(error)) console.error("MainAbility load content failed with error: " + JSON.stringify(error))
}) })
} }
onWindowStageDestroy() { onWindowStageDestroy() {
console.log("MainAbility onWindowStageDestroy") console.log("MainAbility onWindowStageDestroy")
} }
onForeground() { onForeground() {
console.log("MainAbility onForeground") console.log("MainAbility onForeground")
} }
onBackground() { onBackground() {
console.log("MainAbility onBackground") console.log("MainAbility onBackground")
} }
...@@ -114,6 +114,7 @@ The following example shows how an application obtains the bundle code directory ...@@ -114,6 +114,7 @@ The following example shows how an application obtains the bundle code directory
```ts ```ts
import AbilityStage from "@ohos.application.AbilityStage" import AbilityStage from "@ohos.application.AbilityStage"
export default class MyAbilityStage extends AbilityStage { export default class MyAbilityStage extends AbilityStage {
onCreate() { onCreate() {
console.log("MyAbilityStage onCreate") console.log("MyAbilityStage onCreate")
...@@ -188,7 +189,7 @@ export default class MainAbility extends Ability { ...@@ -188,7 +189,7 @@ export default class MainAbility extends Ability {
``` ```
## Starting an Ability ## Starting an Ability
### Available APIs ### Available APIs
The **Ability** class has the **context** attribute, which belongs to the **AbilityContext** class. The **AbilityContext** class has the **abilityInfo**, **currentHapModuleInfo**, and other attributes as well as the APIs used for starting abilities. For details, see [AbilityContext](../reference/apis/js-apis-ability-context.md). The **Ability** class has the **context** attribute, which belongs to the **AbilityContext** class. The **AbilityContext** class has the **abilityInfo**, **currentHapModuleInfo**, and other attributes as well as the APIs used for starting abilities. For details, see [AbilityContext](../reference/apis/js-apis-inner-application-applicationContext.md).
**Table 3** AbilityContext APIs **Table 3** AbilityContext APIs
|API|Description| |API|Description|
......
...@@ -47,242 +47,263 @@ The table below describes the ability call APIs. For details, see [Ability](../r ...@@ -47,242 +47,263 @@ The table below describes the ability call APIs. For details, see [Ability](../r
## How to Develop ## How to Develop
The procedure for developing the ability call is as follows: The procedure for developing the ability call is as follows:
1. Create a callee ability. 1. Create a callee ability.
2. Access the callee ability. 2. Access the callee ability.
### Creating a Callee Ability ### Creating a Callee Ability
For the callee ability, implement the callback to receive data and the methods to marshal and unmarshal data. When data needs to be received, use **on()** to register a listener. When data does not need to be received, use **off()** to deregister the listener. For the callee ability, implement the callback to receive data and the methods to marshal and unmarshal data. When data needs to be received, use **on()** to register a listener. When data does not need to be received, use **off()** to deregister the listener.
**1. Configure the ability launch type.**
Set **launchType** of the callee ability to **singleton** in the **module.json5** file.
|JSON Field|Description| 1. **Configure the ability launch type.**
|:------|:------|
|"launchType"|Ability launch type. Set this parameter to **singleton**.| Set **launchType** of the callee ability to **singleton** in the **module.json5** file.
An example of the ability configuration is as follows: |JSON Field|Description|
```json |:------|:------|
"abilities":[{ |"launchType"|Ability launch type. Set this parameter to **singleton**.|
"name": ".CalleeAbility",
"srcEntrance": "./ets/CalleeAbility/CalleeAbility.ts", An example of the ability configuration is as follows:
"launchType": "singleton",
"description": "$string:CalleeAbility_desc", ```json
"icon": "$media:icon", "abilities":[{
"label": "$string:CalleeAbility_label", "name": ".CalleeAbility",
"visible": true "srcEnty": "./ets/CalleeAbility/CalleeAbility.ts",
}] "launchType": "singleton",
``` "description": "$string:CalleeAbility_desc",
**2. Import the Ability module.** "icon": "$media:icon",
```ts "label": "$string:CalleeAbility_label",
import Ability from '@ohos.app.ability.UIAbility' "exported": true
``` }]
**3. Define the agreed sequenceable data.** ```
The data formats sent and received by the caller and callee abilities must be consistent. In the following example, the data formats are number and string. The code snippet is as follows: 2. **Import the ability module.**
```ts
export default class MySequenceable { ```ts
num: number = 0 import Ability from '@ohos.app.ability.UIAbility';
str: string = "" ```
constructor(num, string) { 3. **Define the agreed sequenceable data.**
this.num = num
this.str = string The data formats sent and received by the caller and callee abilities must be consistent. In the following example, the data formats are number and string. The code snippet is as follows:
}
```ts
marshalling(messageParcel) { export default class MySequenceable {
messageParcel.writeInt(this.num) num: number = 0
messageParcel.writeString(this.str) str: string = ""
return true
} constructor(num, string) {
this.num = num
unmarshalling(messageParcel) { this.str = string
this.num = messageParcel.readInt() }
this.str = messageParcel.readString()
return true marshalling(messageParcel) {
} messageParcel.writeInt(this.num)
} messageParcel.writeString(this.str)
``` return true
**4. Implement Callee.on and Callee.off.** }
The time to register a listener for the callee ability depends on your application. The data sent and received before the listener is registered and that after the listener is deregistered are not processed. In the following example, the **MSG_SEND_METHOD** listener is registered in **onCreate** of the ability and deregistered in **onDestroy**. After receiving sequenceable data, the application processes the data and returns the data result. You need to implement processing based on service requirements. The code snippet is as follows: unmarshalling(messageParcel) {
```ts this.num = messageParcel.readInt()
const TAG: string = '[CalleeAbility]' this.str = messageParcel.readString()
const MSG_SEND_METHOD: string = 'CallSendMsg' return true
}
function sendMsgCallback(data) { }
console.log('CalleeSortFunc called') ```
// Obtain the sequenceable data sent by the caller ability. 4. **Implement Callee.on and Callee.off.**
let receivedData = new MySequenceable(0, '')
data.readSequenceable(receivedData) The time to register a listener for the callee ability depends on your application. The data sent and received before the listener is registered and that after the listener is deregistered are not processed. In the following example, the **MSG_SEND_METHOD** listener is registered in **onCreate** of the ability and deregistered in **onDestroy**. After receiving sequenceable data, the application processes the data and returns the data result. You need to implement processing based on service requirements. The code snippet is as follows:
console.log(`receiveData[${receivedData.num}, ${receivedData.str}]`)
```ts
// Process the data. const TAG: string = '[CalleeAbility]'
// Return the sequenceable data result to the caller ability. const MSG_SEND_METHOD: string = 'CallSendMsg'
return new MySequenceable(receivedData.num + 1, `send ${receivedData.str} succeed`)
} function sendMsgCallback(data) {
console.log('CalleeSortFunc called')
export default class CalleeAbility extends Ability {
onCreate(want, launchParam) { // Obtain the sequenceable data sent by the caller ability.
try { let receivedData = new MySequenceable(0, '')
this.callee.on(MSG_SEND_METHOD, sendMsgCallback) data.readSequenceable(receivedData)
} catch (error) { console.log(`receiveData[${receivedData.num}, ${receivedData.str}]`)
console.log(`${MSG_SEND_METHOD} register failed with error ${JSON.stringify(error)}`)
} // Process the data.
} // Return the sequenceable data result to the caller ability.
return new MySequenceable(receivedData.num + 1, `send ${receivedData.str} succeed`)
onDestroy() { }
try {
this.callee.off(MSG_SEND_METHOD) export default class CalleeAbility extends Ability {
} catch (error) { onCreate(want, launchParam) {
console.error(TAG, `${MSG_SEND_METHOD} unregister failed with error ${JSON.stringify(error)}`) try {
} this.callee.on(MSG_SEND_METHOD, sendMsgCallback)
} } catch (error) {
} console.log(`${MSG_SEND_METHOD} register failed with error ${JSON.stringify(error)}`)
``` }
}
onDestroy() {
try {
this.callee.off(MSG_SEND_METHOD)
} catch (error) {
console.error(TAG, `${MSG_SEND_METHOD} unregister failed with error ${JSON.stringify(error)}`)
}
}
}
```
### Accessing the Callee Ability ### Accessing the Callee Ability
**1. Import the Ability module.** 1. **Import the Ability module.**
```ts
import Ability from '@ohos.app.ability.UIAbility' ```ts
``` import Ability from '@ohos.app.ability.UIAbility';
**2. Obtain the Caller object.** ```
The **context** attribute of the ability implements **startAbilityByCall** to obtain the **Caller** object for communication. The following example uses **this.context** to obtain the **context** attribute of the ability, uses **startAbilityByCall** to start the callee ability, obtain the **Caller** object, and register the **onRelease** listener of the caller ability. You need to implement processing based on service requirements. The code snippet is as follows: 2. **Obtain the Caller object.**
```ts
// Register the onRelease listener of the caller ability. The **context** attribute of the ability implements **startAbilityByCall** to obtain the **Caller** object for communication. The following example uses **this.context** to obtain the **context** attribute of the ability, uses **startAbilityByCall** to start the callee ability, obtain the **Caller** object, and register the **onRelease** listener of the caller ability. You need to implement processing based on service requirements. The code snippet is as follows:
private regOnRelease(caller) {
try { ```ts
caller.on("release", (msg) => { // Register the onRelease listener of the caller ability.
console.log(`caller onRelease is called ${msg}`) private regOnRelease(caller) {
}) try {
console.log('caller register OnRelease succeed') caller.on("release", (msg) => {
} catch (error) { console.log(`caller onRelease is called ${msg}`)
console.log(`caller register OnRelease failed with ${error}`) })
} console.log('caller register OnRelease succeed')
} } catch (error) {
console.log(`caller register OnRelease failed with ${error}`)
async onButtonGetCaller() { }
try { }
this.caller = await context.startAbilityByCall({
bundleName: 'com.samples.CallApplication', async onButtonGetCaller() {
abilityName: 'CalleeAbility' try {
}) this.caller = await context.startAbilityByCall({
if (this.caller === undefined) { bundleName: 'com.samples.CallApplication',
console.log('get caller failed') abilityName: 'CalleeAbility'
return })
} if (this.caller === undefined) {
console.log('get caller success') console.log('get caller failed')
this.regOnRelease(this.caller) return
} catch (error) { }
console.log(`get caller failed with ${error}`) console.log('get caller success')
} this.regOnRelease(this.caller)
} } catch (error) {
``` console.log(`get caller failed with ${error}`)
In the cross-device scenario, you need to specify the ID of the peer device. The code snippet is as follows: }
```ts }
async onButtonGetRemoteCaller() { ```
var caller = undefined
var context = this.context In the cross-device scenario, you need to specify the ID of the peer device. The code snippet is as follows:
context.startAbilityByCall({ ```ts
deviceId: getRemoteDeviceId(), async onButtonGetRemoteCaller() {
bundleName: 'com.samples.CallApplication', var caller = undefined
abilityName: 'CalleeAbility' var context = this.context
}).then((data) => {
if (data != null) { context.startAbilityByCall({
caller = data deviceId: getRemoteDeviceId(),
console.log('get remote caller success') bundleName: 'com.samples.CallApplication',
// Register the onRelease listener of the caller ability. abilityName: 'CalleeAbility'
caller.on("release", (msg) => { }).then((data) => {
console.log(`remote caller onRelease is called ${msg}`) if (data != null) {
}) caller = data
console.log('remote caller register OnRelease succeed') console.log('get remote caller success')
} // Register the onRelease listener of the caller ability.
}).catch((error) => { caller.on("release", (msg) => {
console.error(`get remote caller failed with ${error}`) console.log(`remote caller onRelease is called ${msg}`)
}) })
} console.log('remote caller register OnRelease succeed')
``` }
Obtain the ID of the peer device from **DeviceManager**. Note that the **getTrustedDeviceListSync** API is open only to system applications. The code snippet is as follows: }).catch((error) => {
```ts console.error(`get remote caller failed with ${error}`)
import deviceManager from '@ohos.distributedHardware.deviceManager'; })
var dmClass; }
function getRemoteDeviceId() { ```
if (typeof dmClass === 'object' && dmClass != null) {
var list = dmClass.getTrustedDeviceListSync() Obtain the ID of the peer device from **DeviceManager**. Note that the **getTrustedDeviceListSync** API is open only to system applications. The code snippet is as follows:
if (typeof (list) == 'undefined' || typeof (list.length) == 'undefined') {
console.log("MainAbility onButtonClick getRemoteDeviceId err: list is null") ```ts
return import deviceManager from '@ohos.distributedHardware.deviceManager';
} var dmClass;
console.log("MainAbility onButtonClick getRemoteDeviceId success:" + list[0].deviceId) function getRemoteDeviceId() {
return list[0].deviceId if (typeof dmClass === 'object' && dmClass != null) {
} else { var list = dmClass.getTrustedDeviceListSync()
console.log("MainAbility onButtonClick getRemoteDeviceId err: dmClass is null") if (typeof (list) == 'undefined' || typeof (list.length) == 'undefined') {
} console.log("MainAbility onButtonClick getRemoteDeviceId err: list is null")
} return
``` }
In the cross-device scenario, your application must also apply for the data synchronization permission from end users. The code snippet is as follows: console.log("MainAbility onButtonClick getRemoteDeviceId success:" + list[0].deviceId)
```ts return list[0].deviceId
import abilityAccessCtrl from '@ohos.abilityAccessCtrl.d.ts'; } else {
console.log("MainAbility onButtonClick getRemoteDeviceId err: dmClass is null")
requestPermission() { }
let context = this.context }
let permissions: Array<string> = ['ohos.permission.DISTRIBUTED_DATASYNC'] ```
let atManager = abilityAccessCtrl.createAtManager();
atManager.requestPermissionsFromUser(context, permissions).then((data) => { In the cross-device scenario, your application must also apply for the data synchronization permission from end users. The code snippet is as follows:
console.log("Succeed to request permission from user with data: "+ JSON.stringify(data))
}).catch((error) => { ```ts
console.log("Failed to request permission from user with error: "+ JSON.stringify(error)) import abilityAccessCtrl from '@ohos.abilityAccessCtrl.d.ts';
})
} requestPermission() {
``` let context = this.context
**3. Send agreed sequenceable data.** let permissions: Array<string> = ['ohos.permission.DISTRIBUTED_DATASYNC']
let atManager = abilityAccessCtrl.createAtManager();
The sequenceable data can be sent to the callee ability with or without a return value. The method and sequenceable data must be consistent with those of the callee ability. The following example describes how to send data to the callee ability. The code snippet is as follows: atManager.requestPermissionsFromUser(context, permissions).then((data) => {
```ts console.log("Succeed to request permission from user with data: "+ JSON.stringify(data))
const MSG_SEND_METHOD: string = 'CallSendMsg' }).catch((error) => {
async onButtonCall() { console.log("Failed to request permission from user with error: "+ JSON.stringify(error))
try { })
let msg = new MySequenceable(1, 'origin_Msg') }
await this.caller.call(MSG_SEND_METHOD, msg) ```
} catch (error) {
console.log(`caller call failed with ${error}`) 3. **Send agreed sequenceable data.**
}
} The sequenceable data can be sent to the callee ability with or without a return value. The method and sequenceable data must be consistent with those of the callee ability. The following example describes how to send data to the callee ability. The code snippet is as follows:
```
```ts
In the following, **CallWithResult** is used to send data **originMsg** to the callee ability and assign the data processed by the **CallSendMsg** method to **backMsg**. The code snippet is as follows: const MSG_SEND_METHOD: string = 'CallSendMsg'
```ts async onButtonCall() {
const MSG_SEND_METHOD: string = 'CallSendMsg' try {
originMsg: string = '' let msg = new MySequenceable(1, 'origin_Msg')
backMsg: string = '' await this.caller.call(MSG_SEND_METHOD, msg)
async onButtonCallWithResult(originMsg, backMsg) { } catch (error) {
try { console.log(`caller call failed with ${error}`)
let msg = new MySequenceable(1, originMsg) }
const data = await this.caller.callWithResult(MSG_SEND_METHOD, msg) }
console.log('caller callWithResult succeed') ```
let result = new MySequenceable(0, '') In the following, **CallWithResult** is used to send data **originMsg** to the callee ability and assign the data processed by the **CallSendMsg** method to **backMsg**. The code snippet is as follows:
data.readSequenceable(result)
backMsg(result.str) ```ts
console.log(`caller result is [${result.num}, ${result.str}]`) const MSG_SEND_METHOD: string = 'CallSendMsg'
} catch (error) { originMsg: string = ''
console.log(`caller callWithResult failed with ${error}`) backMsg: string = ''
} async onButtonCallWithResult(originMsg, backMsg) {
} try {
``` let msg = new MySequenceable(1, originMsg)
**4. Release the Caller object.** const data = await this.caller.callWithResult(MSG_SEND_METHOD, msg)
console.log('caller callWithResult succeed')
When the **Caller** object is no longer required, use **release()** to release it. The code snippet is as follows:
```ts let result = new MySequenceable(0, '')
releaseCall() { data.readSequenceable(result)
try { backMsg(result.str)
this.caller.release() console.log(`caller result is [${result.num}, ${result.str}]`)
this.caller = undefined } catch (error) {
console.log('caller release succeed') console.log(`caller callWithResult failed with ${error}`)
} catch (error) { }
console.log(`caller release failed with ${error}`) }
} ```
}
``` 4. **Release the Caller object.**
When the **Caller** object is no longer required, use **release()** to release it. The code snippet is as follows:
```ts
releaseCall() {
try {
this.caller.release()
this.caller = undefined
console.log('caller release succeed')
} catch (error) {
console.log(`caller release failed with ${error}`)
}
}
```
\ No newline at end of file
...@@ -135,7 +135,7 @@ To create a widget in the stage model, you need to implement lifecycle callbacks ...@@ -135,7 +135,7 @@ To create a widget in the stage model, you need to implement lifecycle callbacks
| Name | Description | Data Type | Default Value Allowed | | Name | Description | Data Type | Default Value Allowed |
| ----------- | ------------------------------------------------------------ | ---------- | -------------------- | | ----------- | ------------------------------------------------------------ | ---------- | -------------------- |
| name | Name of the Extension ability. This field must be specified. | String | No | | name | Name of the Extension ability. This field must be specified. | String | No |
| srcEntrance | Path of the Extension ability lifecycle code. This field must be specified.| String | No | | srcEnty | Path of the Extension ability lifecycle code. This field must be specified.| String | No |
| description | Description of the Extension ability. The value can be a string or a resource index to descriptions in multiple languages.| String | Yes (initial value: left empty)| | description | Description of the Extension ability. The value can be a string or a resource index to descriptions in multiple languages.| String | Yes (initial value: left empty)|
| icon | Index of the Extension ability icon file. | String | Yes (initial value: left empty)| | icon | Index of the Extension ability icon file. | String | Yes (initial value: left empty)|
| label | Descriptive information about the Extension ability presented externally. The value can be a string or a resource index to the description.| String | Yes (initial value: left empty)| | label | Descriptive information about the Extension ability presented externally. The value can be a string or a resource index to the description.| String | Yes (initial value: left empty)|
...@@ -150,7 +150,7 @@ To create a widget in the stage model, you need to implement lifecycle callbacks ...@@ -150,7 +150,7 @@ To create a widget in the stage model, you need to implement lifecycle callbacks
```json ```json
"extensionAbilities": [{ "extensionAbilities": [{
"name": "FormAbility", "name": "FormAbility",
"srcEntrance": "./ets/FormAbility/FormAbility.ts", "srcEnty": "./ets/FormAbility/FormAbility.ts",
"label": "$string:form_FormAbility_label", "label": "$string:form_FormAbility_label",
"description": "$string:form_FormAbility_desc", "description": "$string:form_FormAbility_desc",
"type": "form", "type": "form",
......
...@@ -33,8 +33,8 @@ OpenHarmony does not support creation of a Service Extension ability for third-p ...@@ -33,8 +33,8 @@ OpenHarmony does not support creation of a Service Extension ability for third-p
"icon": "$media:icon", "icon": "$media:icon",
"description": "service", "description": "service",
"type": "service", "type": "service",
"visible": true, "exported": true,
"srcEntrance": "./ets/ServiceExtAbility/ServiceExtAbility.ts" "srcEnty": "./ets/ServiceExtAbility/ServiceExtAbility.ts"
}] }]
``` ```
...@@ -44,7 +44,7 @@ OpenHarmony does not support creation of a Service Extension ability for third-p ...@@ -44,7 +44,7 @@ OpenHarmony does not support creation of a Service Extension ability for third-p
```js ```js
import ServiceExtensionAbility from '@ohos.application.ServiceExtensionAbility' import ServiceExtensionAbility from '@ohos.application.ServiceExtensionAbility'
import rpc from '@ohos.rpc' import rpc from '@ohos.rpc'
class StubTest extends rpc.RemoteObject { class StubTest extends rpc.RemoteObject {
constructor(des) { constructor(des) {
super(des); super(des);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册