写点什么

鸿蒙开发丨设备内 UIAbility 的几种交互方式

  • 2023-12-06
    广东
  • 本文字数:3763 字

    阅读完需:约 12 分钟

鸿蒙开发丨设备内UIAbility的几种交互方式

本文分享自华为云社区《设备内UIAbility交互:无缝体验与高级技巧》,作者: 柠檬味拥抱。

UIAbility 组件间交互(设备内)


在设备内,UIAbility(用户界面能力)是系统调度的最小单元,它们负责展示用户界面和执行相关的业务逻辑。设备内的不同功能模块之间的交互是应用程序开发中的重要部分。本文将探讨设备内 UIAbility 之间的交互方式,包括启动应用内的 UIAbility、启动其他应用的 UIAbility 以及通过 Call 调用实现 UIAbility 交互。

启动应用内的 UIAbility


在一个应用内部存在多个 UIAbility 时,可能需要从一个 UIAbility 启动另一个 UIAbility。例如,在支付应用中,从主界面 UIAbility 启动收款 UIAbility。下面是一个示例代码,演示了如何在 EntryAbility 中启动 FuncAbility:


let wantInfo = {    deviceId: '', // deviceId为空表示本设备    bundleName: 'com.example.myapplication',    abilityName: 'FuncAbility',    moduleName: 'module1', // moduleName非必选    parameters: { // 自定义信息        info: '来自EntryAbility Index页面',    },};
// context为调用方UIAbility的AbilityContextthis.context.startAbility(wantInfo).then(() => { // 处理启动成功后的逻辑}).catch((err) => { // 处理启动失败后的逻辑});
复制代码


在 FuncAbility 中,可以通过生命周期回调方法onCreate接收来自 EntryAbility 传递的参数:


import UIAbility from '@ohos.app.ability.UIAbility';import Window from '@ohos.window';
export default class FuncAbility extends UIAbility { onCreate(want, launchParam) { // 接收调用方UIAbility传过来的参数 let funcAbilityWant = want; let info = funcAbilityWant?.parameters?.info; // ... }}
复制代码

启动应用内的 UIAbility 并获取返回结果


有时候,我们希望从一个 UIAbility 启动另一个 UIAbility,并在后者完成业务后获取返回结果。例如,在登录 UIAbility 完成登录操作后,将登录结果返回给主界面 UIAbility。下面是一个示例代码:


let wantInfo = {    deviceId: '', // deviceId为空表示本设备    bundleName: 'com.example.myapplication',    abilityName: 'FuncAbility',    moduleName: 'module1', // moduleName非必选    parameters: { // 自定义信息        info: '来自EntryAbility Index页面',    },};
// context为调用方UIAbility的AbilityContextthis.context.startAbilityForResult(wantInfo).then((data) => { // 处理从FuncAbility返回的结果}).catch((err) => { // 处理启动失败后的逻辑});
复制代码


在 FuncAbility 中,完成业务后需要调用terminateSelfWithResult方法返回结果:


const RESULT_CODE: number = 1001;let abilityResult = {    resultCode: RESULT_CODE,    want: {        bundleName: 'com.example.myapplication',        abilityName: 'FuncAbility',        moduleName: 'module1',        parameters: {            info: '来自FuncAbility Index页面',        },    },};
// context为被调用方UIAbility的AbilityContextthis.context.terminateSelfWithResult(abilityResult, (err) => { // 处理停止自身后的逻辑});
复制代码


在调用方的回调中可以获取返回的结果:


const RESULT_CODE: number = 1001;
// ...
// context为调用方UIAbility的AbilityContextthis.context.startAbilityForResult(want).then((data) => { if (data?.resultCode === RESULT_CODE) { // 解析被调用方UIAbility返回的信息 let info = data.want?.parameters?.info; // 处理返回的结果 }}).catch((err) => { // 处理启动失败后的逻辑});
复制代码

启动其他应用的 UIAbility


有时候,我们需要启动其他应用的 UIAbility。这可以通过隐式 Want 启动实现,系统会根据调用方提供的条件匹配适当的 UIAbility。



let wantInfo = {    deviceId: '', // deviceId为空表示本设备    action: 'ohos.want.action.viewData',    entities: ['entity.system.default'],};
// context为调用方UIAbility的AbilityContextthis.context.startAbility(wantInfo).then(() => { // 处理启动成功后的逻辑}).catch((err) => { // 处理启动失败后的逻辑});
复制代码

启动其他应用的 UIAbility 并获取返回结果


如果需要获取其他应用 UIAbility 的返回结果,可以使用startAbilityForResult方法:


let wantInfo = {    deviceId: '', // deviceId为空表示本设备    action: 'ohos.want.action.editData',    entities: ['entity.system.default'],};
// context为调用方UIAbility的AbilityContextthis.context.startAbilityForResult(wantInfo).then((data) => { // 处理从其他应用UIAbility返回的结果}).catch((err) => { // 处理启动失败后的逻辑});
复制代码


在被调用方的 UIAbility 中,需要调用terminateSelfWithResult方法返回结果:


const RESULT_CODE: number = 1001;let abilityResult = {    resultCode: RESULT_CODE,    want: {        bundleName: 'com.example.myapplication',        abilityName: 'EntryAbility',        moduleName: 'entry',        parameters: {            payResult: 'OKay',        },    },};
// context为被调用方UIAbility的AbilityContextthis.context.terminateSelfWithResult(abilityResult, (err) => { // 处理停止自身后的逻辑});
复制代码


在调用方的回调中可以获取返回的结果:


const RESULT_CODE: number = 1001;
// ...
// context为调用方UIAbility的AbilityContextthis.context.startAbilityForResult(want).then((data) => { if (data?.resultCode === RESULT_CODE) { // 解析被调用方UIAbility返回的信息 let payResult = data.want?.parameters?.payResult; // 处理返回的结果 }}).catch((err) => { // 处理启动失败后的逻辑});
复制代码


这些示例展示了在设备


内进行 UIAbility 之间交互的常见场景和方法,希望对您的应用程序开发有所帮助。

通过 Call 调用实现 UIAbility 交互(仅对系统应用开放)


在某些情况下,需要通过Call调用来实现 UIAbility 之间的交互。这种方式通常仅对系统应用开放。以下是一个简单的示例,演示了如何通过Call调用实现 UIAbility 的交互:



let wantInfo = {    deviceId: '', // deviceId为空表示本设备    abilityName: 'SystemAbility',    parameters: {        operation: 'performTask',        task: 'someTask',    },};
// context为调用方UIAbility的AbilityContextthis.context.call(wantInfo).then((data) => { // 处理Call调用返回的结果}).catch((err) => { // 处理Call调用失败后的逻辑});
复制代码


在被调用方的 UIAbility 中,需要实现onCall方法来处理 Call 调用:


import UIAbility from '@ohos.app.ability.UIAbility';
export default class SystemAbility extends UIAbility { onCall(message) { // 处理Call调用传递过来的信息 let operation = message?.operation; let task = message?.task; // ... // 返回Call调用的结果 return { result: 'Task performed successfully', }; }}
复制代码


这里使用了onCall方法来处理调用传递过来的信息,并返回相应的结果。


总体而言,通过startAbilitystartAbilityForResultcall等方法,UIAbility 之间可以实现灵活的交互,满足各种应用场景的需求。在实际开发中,需要根据具体业务需求选择合适的方式进行 UIAbility 之间的通信,并确保良好的用户体验和应用的稳定性。


注意事项与最佳实践


在进行 UIAbility 之间的交互时,开发者应该注意一些重要的事项和最佳实践,以确保应用程序的性能、稳定性和用户体验。


  1. 权限和安全性: 确保对敏感信息和操作进行适当的权限检查,以保障用户隐私和应用的安全性。合理使用能力分级和权限管理机制。

  2. 错误处理: 对于 UIAbility 之间的交互,及时而有效的错误处理是至关重要的。在使用catch捕获错误时,可以提供友好的用户提示或记录详细的日志以便追踪和调试。

  3. 业务场景设计: 在设计 UIAbility 之间的交互时,充分考虑业务场景和用户行为。确保交互逻辑符合用户的预期,提高用户体验。

  4. 数据传递: 良好的数据传递机制是 UIAbility 之间交互的核心。在传递数据时,要确保数据的准确性、完整性,并进行必要的验证。

  5. 生命周期管理: 注意 UIAbility 的生命周期管理,合理使用startAbilityForResultterminateSelfWithResult等方法,确保 UIAbility 的启动和停止顺序合理。

  6. 异步编程: 由于 UIAbility 之间的交互通常是异步的,确保在合适的时机处理异步回调,避免阻塞用户界面。

  7. 性能优化: 对于频繁启动和停止 UIAbility 的情况,考虑性能优化,减少资源消耗,提高应用响应速度。

  8. 代码规范: 遵循良好的代码规范和开发规范,使代码易读、易维护,并且能够适应未来的扩展和更新。


在实际应用中,以上这些建议可以根据具体的业务需求进行调整和扩展。通过合理的 UIAbility 之间的交互,开发者可以实现更加丰富和复杂的应用功能,为用户提供更好的使用体验。


点击关注,第一时间了解华为云新鲜技术~

发布于: 刚刚阅读数: 3
用户头像

提供全面深入的云计算技术干货 2020-07-14 加入

生于云,长于云,让开发者成为决定性力量

评论

发布
暂无评论
鸿蒙开发丨设备内UIAbility的几种交互方式_鸿蒙_华为云开发者联盟_InfoQ写作社区