尧图网站设计 尧图网站设计YAOTU DESIGN
ARTICLE DETAIL

资讯详情

深耕网站设计与一线实操的经验洞察。

HarmonyOS 互动卡片通信架构:三方跨进程数据传递与状态回推全解析

HarmonyOS 互动卡片通信架构:三方跨进程数据传递与状态回推全解析 HarmonyOS 互动卡片通信架构三方跨进程数据传递与状态回推全解析前言互动卡片里最容易出 bug 的不是动画而是数据从哪来到哪去。动态卡片、宿主应用、互动卡片激活态 UI三者不在同一进程、生命周期也各管各的通信方式选错轻则收不到数据、重则直接失效。本文作为互动卡片系列的第三篇将系统拆解三方通信架构——从动态卡片到应用页面跳转、从应用到卡片数据推送、从互动卡片到动态卡片状态回推再到跨进程持久化存储逐一讲解每种通信方式的核心 API 和适用场景。一、三方通信架构全景1.1 通信角色与关系互动卡片涉及三个独立角色它们之间需要多种通信方式协作图互动卡片三方通信架构——动态卡片、应用、互动卡片之间的多种通信方式角色进程生命周期管理方动态卡片非激活态独立进程卡片在桌面时存活FormExtensionAbility宿主应用主进程应用前台/后台EntryAbility互动卡片激活态独立进程激活期间存活LiveFormExtensionAbility1.2 七种通信方式总览通信方向方式核心 API说明动态卡片 → 应用页面跳转postCardAction(ROUTER)点击卡片跳转到应用页面动态卡片 → 应用方法调用postCardAction(CALL)通过callee监听调用应用方法动态卡片 → FormExtensionAbility发送消息postCardAction(MESSAGE)通过onFormEvent接收处理应用 → 动态卡片数据推送formProvider.updateFormformBindingData键值对自动映射到LocalStorageProp应用 → 互动卡片数据持久化用户首选项/RDB/文件存储跨进程通信LiveFormExtensionAbility 读取互动卡片内部共享存储LocalStorage同进程内传递初始数据互动卡片 → 动态卡片数据回推formProvider.updateForm实况卡片状态变化回推到动态卡片二、动态卡片 → 应用通信2.1 页面跳转ROUTER最常用的通信方式用户点击卡片跳转到应用指定页面// 在卡片 UI 中调用postCardAction(this,{action:router,abilityName:EntryAbility,params:{targetPage:DeliveryPage// 目标页面名称}});封装为工具方法exportclassActionUtils{/** * 卡片跳转到应用页面 */staticjumpAppPage(component:object,pageName:string):void{postCardAction(component,{action:router,abilityName:EntryAbility,params:{targetPage:pageName}});}}2.2 方法调用CALL卡片直接调用应用中的方法通过callee监听实现// 1. 卡片端发送 CALL 请求postCardAction(this,{action:call,abilityName:EntryAbility,params:{method:playMusic,songId:12345}});// 2. 应用端在 EntryAbility 中注册 callee 监听import{UIAbility,Want}fromkit.AbilityKit;exportdefaultclassEntryAbilityextendsUIAbility{onCreate(want:Want):void{this.callee.on(call,(indata){constmethodindata.parameters.methodasstring;switch(method){caseplayMusic:this.handlePlayMusic(indata.parameters.songId);break;casepauseMusic:this.handlePauseMusic();break;}});}privatehandlePlayMusic(songId:string):void{console.info(播放音乐:${songId});}privatehandlePauseMusic():void{console.info(暂停音乐);}}三、动态卡片 → FormExtensionAbility 通信3.1 消息发送MESSAGE卡片通过postCardAction(MESSAGE)发送消息到FormExtensionAbility这是互动卡片激活的关键路径// 卡片端发送消息constparams{message:requestOverflow,widthRatio:1.3,heightRatio:1.3,duration:5000};postCardAction(this,{action:message,message:JSON.stringify(params)});// FormExtensionAbility 端接收消息asynconFormEvent(formId:string,message:string):Promisevoid{constparamsJSON.parse(message);constmsgTypeparams.messageasstring;if(msgTyperequestOverflow){awaitthis.requestOverflow(formId,params.widthRatio,params.heightRatio,params.duration);}}四、应用 → 动态卡片数据推送4.1 formProvider.updateForm应用通过formProvider.updateForm向动态卡片推送数据数据自动映射到卡片的LocalStorageProp变量import{formProvider,formBindingData}fromkit.FormKit;/** * 应用向动态卡片推送数据 */asyncfunctionupdateCardData(formId:string,data:Recordstring,Object):Promisevoid{try{constbindingDataformBindingData.createFormBindingData(data);awaitformProvider.updateForm(formId,bindingData);console.info(卡片数据更新成功);}catch(err){console.error(卡片数据更新失败:${JSON.stringify(err)});}}// 使用示例更新睡眠卡片状态awaitupdateCardData(formId,{isSleep:false,sleepTime:07:30,wakeStatus:按时起床});// 卡片端接收数据EntryComponentstruct SleepCard{LocalStorageProp(isSleep)isSleep:booleantrue;LocalStorageProp(sleepTime)sleepTime:string07:00;LocalStorageProp(wakeStatus)wakeStatus:string;build(){Column(){Image(this.isSleep?$rawfile(sleep/sleep_hanhan.png):$rawfile(sleep/wake_hanhan.png)).width(60%).height(60%)Text(this.isSleep?睡眠中:this.wakeStatus).fontSize(14).fontColor(#666)}}}五、应用 → 互动卡片跨进程数据持久化5.1 三种持久化方案应用与互动卡片激活态 UI在不同进程需要使用持久化存储传递数据方案API适用场景性能用户首选项Preferenceskit.ArkData简单键值对开关状态快关系型数据库RDBkit.ArkData结构化数据歌曲列表中文件存储kit.CoreFileKit大量数据或上下文中5.2 用户首选项存储import{preferences}fromkit.ArkData;/** * 应用端保存运动状态 */exportclassExerciseStateManager{privatestaticreadonlyPREF_NAMEexercise_state;staticasyncsaveExerciseState(state:ExerciseState):Promisevoid{constprefsawaitpreferences.getPreferences(getContext(),ExerciseStateManager.PREF_NAME);awaitprefs.put(isExercising,state.isExercising);awaitprefs.put(calories,state.calories);awaitprefs.flush();}staticasyncgetExerciseState():PromiseExerciseState{constprefsawaitpreferences.getPreferences(getContext(),ExerciseStateManager.PREF_NAME);return{isExercising:prefs.get(isExercising,false)asboolean,calories:prefs.get(calories,0)asnumber};}}interfaceExerciseState{isExercising:boolean;calories:number;}5.3 关系型数据库存储音乐卡片使用 RDB 存储歌曲列表和收藏状态实现跨进程数据同步import{relationalStore}fromkit.ArkData;/** * 音乐卡片数据管理器RDB */exportclassMusicDataManager{privatestaticstore:relationalStore.RdbStore|nullnull;staticasyncinitDatabase(context:Context):Promisevoid{constconfig:relationalStore.StoreConfig{name:MusicCard.db,securityLevel:relationalStore.SecurityLevel.S1};MusicDataManager.storeawaitrelationalStore.getRdbStore(context,config);// 创建歌曲表awaitMusicDataManager.store.executeSql(CREATE TABLE IF NOT EXISTS songs ( id TEXT PRIMARY KEY, title TEXT NOT NULL, artist TEXT NOT NULL, isFavorite INTEGER DEFAULT 0 ));}staticasyncgetSongs():PromiseSongInfo[]{constresultSetawaitMusicDataManager.store!.querySql(SELECT * FROM songs);constsongs:SongInfo[][];while(resultSet.goToNextRow()){songs.push({id:resultSet.getString(0),title:resultSet.getString(1),artist:resultSet.getString(2),isFavorite:resultSet.getLong(3)1});}resultSet.close();returnsongs;}staticasyncupdateFavorite(songId:string,isFavorite:boolean):Promisevoid{awaitMusicDataManager.store!.executeSql(UPDATE songs SET isFavorite ? WHERE id ?,[isFavorite?1:0,songId]);}}interfaceSongInfo{id:string;title:string;artist:string;isFavorite:boolean;}六、互动卡片 → 动态卡片状态回推6.1 状态回推机制互动卡片激活态中状态变化后需要通过formProvider.updateForm将状态回推到动态卡片确保非激活态显示正确的状态// 在互动卡片 UI 中回推状态import{formProvider,formBindingData}fromkit.FormKit;/** * 互动卡片状态回推到动态卡片 */asyncfunctionpushStateBackToCard(formId:string,state:Recordstring,Object):Promisevoid{try{constbindingDataformBindingData.createFormBindingData(state);awaitformProvider.updateForm(formId,bindingData);console.info(状态回推成功:${JSON.stringify(state)});}catch(err){console.error(状态回推失败:${JSON.stringify(err)});}}// 睡眠卡片动画结束后回推 isSleep 状态awaitpushStateBackToCard(this.formId,{isSleep:false,wakeStatus:按时起床});// 运动卡片运动结束后回推卡路里数据awaitpushStateBackToCard(this.formId,{calories:300,isExercising:false});6.2 四种卡片的状态回推卡片回推内容触发时机睡眠卡片isSleep、wakeStatus起床动画结束后快递卡片无需回推状态无变化-运动卡片calories、isExercising运动结束后音乐卡片当前歌曲、播放状态切歌、播放状态变化时七、互动卡片内部 LocalStorage 传递7.1 LocalStorage 传递初始数据LiveFormExtensionAbility通过LocalStorage向互动卡片 UI 传递初始数据// LiveFormExtensionAbility 中设置 LocalStorageonLiveFormCreate(liveFormInfo:LiveFormInfo,session:UIExtensionContentSession):void{conststorage:LocalStoragenewLocalStorage();// 传递上下文storage.setOrCreate(context,this.context);storage.setOrCreate(session,session);// 传递卡片信息storage.setOrCreate(formId,liveFormInfo.formId);storage.setOrCreate(borderRadius,liveFormInfo.borderRadius);storage.setOrCreate(formRect,liveFormInfo.rect);// 加载 UIsession.loadContent(livecardability/pages/DeliveryLiveCard,storage);}// 互动卡片 UI 中读取Entry({useSharedStorage:true})Componentstruct DeliveryLiveCard{LocalStorageProp(formRect)rect?:formInfo.Rectundefined;LocalStorageProp(borderRadius)radius:number0;LocalStorageProp(formId)formId:string;build(){Stack({alignContent:Alignment.TopStart}){Image($rawfile(delivery/background.png)).borderRadius(this.radius).width(this.rect?.width||0).height(this.rect?.height||0)}}}八、通信方式选型指南8.1 选型决策树场景推荐方式原因卡片跳转应用页面postCardAction(ROUTER)直接、简单卡片调用应用方法postCardAction(CALL)支持方法调用和返回卡片触发激活动画postCardAction(MESSAGE)必须经过 FormExtensionAbility应用推送数据到卡片formProvider.updateForm唯一方式应用传递数据到互动卡片用户首选项/RDB/文件跨进程持久化互动卡片回推状态formProvider.updateForm确保非激活态正确8.2 各卡片使用的通信方式卡片通信方式组合睡眠卡片ROUTER跳转页面 MESSAGE触发动画updateForm回推 isSleep LocalStorage内部传递音乐卡片CALL播放控制 ROUTER跳转页面 MESSAGE触发动画 RDB歌曲数据updateForm同步状态运动卡片CALL运动控制 ROUTER跳转页面 MESSAGE触发动画 文件存储运动状态updateForm回推卡路里快递卡片ROUTER跳转页面 MESSAGE触发动画 LocalStorage内部传递九、总结本文系统拆解了互动卡片的三方通信架构七种通信方式ROUTER、CALL、MESSAGE、updateForm、持久化存储、LocalStorage、状态回推动态卡片 → 应用页面跳转ROUTER和方法调用CALL两种方式应用 → 动态卡片唯一方式formProvider.updateFormformBindingData应用 → 互动卡片三种持久化方案Preferences / RDB / 文件存储互动卡片 → 动态卡片formProvider.updateForm状态回推确保非激活态正确显示下一篇将以快递卡片和睡眠卡片为主线深入讲解完整开发流程与帧动画、陀螺仪交互、破框效果的实战实现。如果这篇文章对你有帮助欢迎点赞、收藏⭐、关注你的支持是我持续创作的动力相关资源互动卡片开发实践文档华为开发者文档互动卡片示例代码GitCode用户首选项开发华为开发者文档关系型数据库开发华为开发者文档开源鸿蒙跨平台社区CSDN 社区
返回列表