当前位置: 首页 > 科技观察

鸿蒙OS流通跨设备迁移

时间:2023-03-21 17:19:21 科技观察

更多内容请访问:鸿蒙技术社区https://harmonyos.51cto.com,与华为官方共同建立,也是鸿蒙OS的一大看点。迁移根据体验可分为跨设备迁移和多设备协同。这里我主要告诉大家如何进行跨设备迁移,以及我在项目开发过程中遇到的问题和解决方法。具体概念这里就不多说了,大家可以参考官方文档。开发步骤在开发过程中,我们可以根据业务需求分为以下两种场景:同一个FA(Ability1—Ability1)之间的迁移;不同FA之间的迁移(能力1—能力2)。下面分别介绍一下以上两种场景的具体开发步骤。同一个FA之间的迁移同一个FA之间的迁移是指在不同的设备上安装同一个FA。官方文档有详细的开发步骤。下面只会告诉大家需要注意的地方和我遇到的情况。问题不让大家踩坑。1、我们创建FA之后,因为我们大部分的业务逻辑都在AbilitySlice中,所以我们必须在Ability和AbilitySlice中实现IAbilityContinuation接口,在Ability中实现onStartContinuation()和onSaveData(IntentParamsintentParams),onRestoreData(的返回值IntentParamsintentParams)都设置为true。publicclassMainAbilityextendsAbilityimplementsIAbilityContinuation{@OverridepublicbooleanonStartContinuation(){returntrue;}@OverridepublicbooleanonSaveData(IntentParamsintentParams){returntrue;}@OverridepublicbooleanonRestoreData(IntentParamsintentParams){returntrue;}/省略配置相应的权限,同样需要在代码中动态申请。"reqPermissions":[{"name":"ohos.permission.DISTRIBUTED_DATASYNC"},{"name":"ohos.permission.DISTRIBUTED_DEVICE_STATE_CHANGE"},{"name":"ohos.permission.GET_DISTRIBUTED_DEVICE_INFO"},{"name":"ohos.permission.GET_BUNDLE_INFO"}]if(canRequestPermission(SystemPermission.DISTRIBUTED_DATASYNC)){//是否可以申请弹窗授权(第一次申请或者用户没有选择禁止不再提示)requestPermissionsFromUser(newString[]{SystemPermission.DISTRIBUTED_DATASYNC},PERMISSIONS_REQUEST_DISTRIBUTED);}3.定义相关参数,设置传输任务管理服务回调函数,注册传输任务管理服务,管理传输目标设备,传输结束需要注销传输任务管理服务。//转账应用包名privateStringBUNDLE_NAME="XXX.XXX.XXX";//注册转账任务管理服务后返回的AbilitytokenprivateintabilityToken;//用户在设备列表中选择设备后返回的设备IDprivateStringselectDeviceId;//获取转账任务managementservice管理类privateIContinuationRegisterManagercontinuationRegisterManager;//设置流转任务管理服务设备状态变更的回调privateIContinuationDeviceCallbackcontinuationDeviceCallback=newIContinuationDeviceCallback(){@OverridepublicvoidonDeviceConnectDone(StringdeviceId,StringdeviceType){selectDeviceId=deviceId;continuationRegisterManager.updateConnectStatus(abilityToken,selectDeviceId,DeviceConnectState.CONNECTING.getState(),null);...}@OverridepublicvoidonDeviceDisconnectDone(Strings){getUITaskDispatcher().asyncDispatch(()->{continuationRegisterManager.updateConnectStatus(abilityToken,selectDeviceId,DeviceConnectState.DIS_CONNECTING.getState(),null);});unRegisterContinuation();};//设置注册转移任务管理服务回调privateRequestCallbackrequestCallback=newRequestCallback(){@OverridepublicvoidonResult(intresult){abilityToken=result;}};...@OverridepublicvoidonStart(Intentintent){...continuationRegisterManager=getContinuationRegisterManager();}@OverridepublicvoidonStop(){super.onStop();//注销转移任务管理服务continuationRegisterManager.unregister(abilityToken,null);//断开中转任务管理服务连接continuationRegisterManager.disconnect();}在Api5中,IContinuationDeviceCallback的回调接口与官方文档有些不同。当你选择一个设备时,会返回你在onDeviceConnectDone中选择的设备ID和设备类型4.注册转账服务后,我们可以调出系统转账选择设备弹窗,通过ExtraParams过滤设备。如果不需要过滤,则不需要通过。ExtraParamsparams=newExtraParams();String[]devTypes=newString[]{ExtraParams.DEVICETYPE_SMART_PHONE,ExtraParams.DEVICETYPE_SMART_WATCH,ExtraParams.DEVICETYPE_SMART_PAD};params.setDevType(devTypes);registerContinuation();/ListDeviceType_SMART_PAD};params.setDevType(d.setDevType)注册继续();,params,newRequestCallback(){@OverridepublicvoidonResult(intresult){}});5、选择设备后,会通过上述IContinuationDeviceCallback的onDeviceConnectDone方法回调,然后通过continueAbility方法传入目标设备的DeviceID,将正在运行的FA迁移到目标设备,实现无缝迁移设备之间的服务。//设置流转任务管理服务设备状态变更的回调privateIContinuationDeviceCallbackcontinuationDeviceCallback=newIContinuationDeviceCallback(){@OverridepublicvoidonDeviceConnectDone(StringdeviceId,StringdeviceType){selectDeviceId=deviceId;getUITaskDispatcher().asyncDispatch(()->{continuationRegisterManager.updateConnectStatus(abilityToken,selectDeviceId,DeviceConnectState.CONNECTING.getState(),null);});if(selectDeviceId!=null){continueAbility(selectDeviceId);}...}@OverridepublicvoidonDeviceDisconnectDone(Strings){...unRegisterContinuation();}};6.在FA迁移中我认为最重要的部分是状态和数据的转移。为了让用户体验到“无缝”的用户体验,需要通过实现IAbilityContinuation接口来实现数据的传递。主要代码如下:@OverridepublicbooleanonSaveData(IntentParamssaveData){//根据业务需求,在这里设置需要传输的数据saveData.setParam("continueParam",continueParam);returntrue;}@OverridepublicbooleanonRestoreData(IntentParamsrestoreData){//RemoteFA迁移状态数据,开发者可以按照自己的业务处理这些数据Objectdata=restoreData.getParam("continueParam");getUITaskDispatcher().asyncDispatch(()->{});returntrue;}需要注意的是,onRestoreData处理数据更新UI时,需要在UI线程中更新,否则会报错MigrationbetweendifferentFAsinmightbeinmigration实际开发由于设备端的一些需求和不同的UI,比如车机、手机、手表,开发了不同的FA。不同FA之间的迁移和同一个FA之间的迁移配置几乎一样,只是我们的AbilitySlice不需要实现IAbilityContinuation接口来实现数据同步,而是通过Intent。具体实现如下。1.首先,我们在设备选择成功后通过回调IContinuationDeviceCallback初始化分布式环境。//设置中转任务管理服务设备状态变化的回调分布式环境DeviceManager.initDistributedEnvironment(selectDeviceId,newIInitCallback(){@OverridepublicvoidonInitSuccess(Stringsuccess){}@OverridepublicvoidonInitFailure(Stringfailure,intresult){}});}catch(RemoteExceptione){e.printStackTrace();}...}。..};2。之前,我们跳过了continueAbility()方法,现在我们需要跳过Intent方法。Intentintent=newIntent();Operationoperation=newIntent.OperationBuilder().withDeviceId(deviceId).withBundleName(bundleName).withAbilityName(abilityName).withFlags(Intent.FLAG_ABILITYSLICE_MULTI_DEVICE).build();intent.setOperation(operation);IntentParams=newintentParams();//通过IntentParams传递参数...startAbility(intent);在接收端,我们可以通过onStart(Intentintent)方法接受传入的参数,然后根据自己的业务逻辑实现数据同步。自定义设备选择弹窗在实际项目开发中,我们也可以自定义流程弹窗样式,但是不推荐这种方式。经测试发现只有两台设备通过蓝牙连接才能获取到设备列表。在具体场景下,比如手机和车机,手机和手表,我们在实际使用的时候基本都会保持一个蓝牙连接,这样流量会更稳定。但如果无法保持蓝牙实时连接,则不推荐使用。1、官方API提供了DeviceManager.getDeviceList()获取远程设备。具体代码如下:publicstaticListgetDeviceList(){//调用DeviceManager的getDeviceList接口,通过FLAG_GET_ONLINE_DEVICE标志获取在线设备列表ListonlineDevices=DeviceManager.getDeviceList(DeviceInfo.FLAG_GET_ONLINE_DEVICE);//判断联网设备是否为空if(onlineDevices==null){LogUtil.e(TAG,"onlinedevicesisnull");returnnewArrayList<>();}returnonlineDevices;}2.获取到设备列表后,我们可以自己实现页面,只需要将上面showDeviceList()中弹出设备列表的位置换成我们自己的弹窗即可。效果展示结论目前DevEcoStudio2.1Release及以上版本已经支持模拟器进行跨端口移植。如果没有显示,可以在设置-DevEcoLabs中勾选EnableSuperDevice。文章相关附件可点击下方链接下载原文:https://harmonyos.51cto.com/resource/1426更多信息请访问:与华为共建的鸿蒙技术社区,https://和谐。51cto.com