文章目录
官方适配库会有一个readme文档,记录了不同Flutter版本对应的三方库适配版本,虽然官方适配库的数量越来越多,但是依然有相当数量的三方库没有适配鸿蒙,这时候就需要我们通过桥接来完成对鸿蒙的适配。
适配链接可查看适配进度:项目文件预览 - flutter_packages - GitCode
根据实际项目需求适配
因为每个三方库实现的业务逻辑不一样,所以没有固定的公式,但有一套相似的逻辑,最终差异点在具体的库功能上
一、适配前期准备
有一些库不在官方的适配单上,属于是比较小众的库,只能靠自己适配
1.1 创建ohos模块
命令:flutter create --platforms ohos,android,ios --org <org> <appName>
步骤:
- 1)用VsCode打开刚刚下载好的插件
- 2)打开文件所在位置并打开终端
- 3)通过命令行创建ohos模块
flutter create --platforms ohos path_provider_ohos
flutter create . --template=plugin --platforms=ohos
执行效果如下:
Tips :要保证命名使用小写英文字母,不使用大写,否则创建ohos这块好像有点问题
创建好之后,可以查看ohos文件里的构成
1.2 完善创建配置
在三方库的pubspec.yaml文件的flutter:下添加ohos
到此ohos部分就正式建立好了。
三方库文件结构如下图:
这样适配三方库的前期工作就准备好了,接下来开始着手准备适配
二、适配闭源库
2.1 生成功能模块介绍
创建好后查看ohos文件夹下,src里的.ets后缀结尾的文件
可以看到生成了一个包含基础适配的代码框架:
其中导入的部分主要是这些:
我将分别介绍下基础架构的部分:
- import引入部分从
@ohos/flutter_ohos
导入了Flutter插件开发所需的核心接口和类,包括:FlutterPlugin
:表示一个Flutter插件。FlutterPluginBinding
:提供插件与Flutter引擎之间的绑定信息。MethodCall
、MethodCallHandler
、MethodChannel
、MethodResult
:用于处理Flutter与原生代码之间的方法调用和通信。
- GetuiflutPlugin类实现了
FlutterPlugin
和MethodCallHandler
接口,表明它是一个可以处理Flutter方法调用的插件。 - channel:一个
MethodChannel
类型的私有属性,用于Flutter与原生代码之间的通信。 - constructor:构造函数,当前为空,可用于初始化插件实例。
- getUniqueClassName 方法:返回插件的唯一类名,这里是"GetuiflutPlugin"。
- onAttachedToEngine方法:
- 插件被附加到Flutter引擎时调用。
- 创建一个名为"getuiflut"的方法通道,并设置当前插件为该通道的方法调用处理器。
- onDetachedFromEngine方法:
- 插件从Flutter引擎分离时调用。
- 清除方法通道的处理器,释放资源。
- onMethodCall 方法:
- 处理来自Flutter的方法调用。
- 当前仅处理"getPlatformVersion"方法,返回字符串"OpenHarmony ^ ^ ",表示当前平台是OpenHarmony。
- 对于其他未实现的方法,调用
result.notImplemented()
表示不支持。
2.2 适配的几种情况
具体到适配方式有几种情况,我列举分析下:
-
第一种是三方闭源库,有官方适配的har包,比如网易易盾、旷视,这种相对来说较为简单,引入一下har包,导入直接使用,参考安卓和IOS端逻辑,完成鸿蒙适配。
-
第二种也是三方闭源库,但官方没有适配原生鸿蒙的har包,这种就相对麻烦一点,比如友盟推送,逻辑上写起来需要对安卓和IOS端逻辑理解较为深刻,难度较高。
2.3 正式开始适配
我这里用getuiflut库举个例子,官方适配计划的文档上没有,需要自己适配。
2.3.1 GetuiflutPlugin 类
鸿蒙端适配只需要考虑到鸿蒙即可,也不用动其他端的代码,参考lib文件夹下的文件,可适当参考安卓的适配逻辑
GetuiflutPlugin 类是实现 FlutterPlugin
和 MethodCallHandler
接口,负责插件的生命周期管理
- 一般构造函数里不需要写逻辑,可以加一个日志
constructor() {
console.log('接通了')
}
- getUniqueClassName方法里也不用写什么逻辑
getUniqueClassName(): string {
return "GetuiflutPlugin"
}
- onAttachedToEngine是注册通道
一般用来初始化方法通道和初始化事件通道,这里可以参考安卓的逻辑,假如安卓只有方法通道没有时间通道,那鸿蒙侧就只添加上方法通道不添加时间通道,例如getuiflut这个三方库
安卓端此处逻辑:
可以看到只有方法通道,所以我们在鸿蒙侧可以写:
onAttachedToEngine(binding: FlutterPluginBinding): void {
this.channel = new MethodChannel(binding.getBinaryMessenger(), "getuiflut");
this.channel.setMethodCallHandler(this)
}
- onDetachedFromEngine是取消注册通道
取消通道可以这么写
onDetachedFromEngine(binding: FlutterPluginBinding): void {// 取消注册通道
if (this.channel != null) {
this.channel .setMethodCallHandler(null)
}
Log.d("flutterHandler", "GetuiflutPlugin onDetachedFromEngine ");
}
置空即可
- onMethodCall是处理来自 Flutter 的方法调用
安卓里是通过if…else…来判断flutter调用的是哪个原生方法:
鸿蒙也可按照这个模式写,也可用switch,个人倾向于使用switch:
我截取了部分供参考,可以看到基本是按照其他端的逻辑完成鸿蒙端的适配。
2.3.2 SDK 的各种功能接口
接下来需要对照lib下文件夹里的文件里的功能进行
例如getuiflut这个三方库
我列举其中几个做例子,
- initGtSdk(): 初始化个推 SDK
- getClientId(): 获取客户端 ID
- bindAlias(), unbindAlias(): 别名绑定/解绑
- setTag(): 设置标签
- setBadge(): 设置角标
这些方法是在安卓里有的,鸿蒙侧的根据项目实际需求选择需要的适配即可
有一点需要说明的是,有些库属于闭源库,某些国内的业务供应商会有适配鸿蒙的SDK,只需要集成其适配的har包,更容易开发一点;第二种是没有适配鸿蒙那就需要参考安卓和IOS的逻辑写。
比如initGtSdk方法,安卓里是这样的:
鸿蒙侧我们可以这样实现:
private initGtSdk(): void {
console.log('initGtSdk进来了');
// 开启应用通知开关
const context1 = getContext() as common.UIAbilityContext;
console.log('获取上下文成功');
notificationManager.requestEnableNotification(context1).then(() => {
//初始化GTSDK
PushManager.initialize({
context: context1 as common.UIAbilityContext,
onSuccess: (cid:string) => {
console.log('个推SDK初始化成功'+cid)
},
onFailed: (error:string) => {
console.log('个推SDK初始化失败'+error)
}
})
}).catch((err: BusinessError) => {
console.log('开启通知权限失败'+err)
})
}
用鸿蒙的语法写出来,PushManager及其所属方法就是使用了鸿蒙har包,通过引入即可使用,在ohos目录下并创建一个libs文件夹,har包放libs里即可。
三、总结
相较于原生鸿蒙开发,已有flutter项目适配鸿蒙性价比较高,出成果的速度也快,当然了适配这一块对开发人员的要求也更高,就像适配从前期准备到实际适配中间的坑比较多,网络上也没有比较完整的文档,全靠社区经验和摸索,有不懂的可以私信问我。