不学Flutter,我们来用Kotlin KMM跨平台吧
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了不学Flutter,我们来用Kotlin KMM跨平台吧相关的知识,希望对你有一定的参考价值。
参考技术A 官方推荐有三种不同的方法来组织团队在多平台库上的工作方式:我觉得 1 比较适合,当然大公司 3 也适合,毕竟跨平台的共享模块是 kotlin 语言开发的。
在我们的 shared 里面,当然这个名字是我自己起的,androidApp 和 iosApp 也是可以自己起。我们看看新建一个 KMM 工程是什么样子。
Finish 就可以看到我们上述的文件界面了。
感觉还是不错的,而且和 flutter 和 RN 走的路线也不太一样。KMM 的当前的方式更多的是可以将一些逻辑层统一,比如 MVP 中的 M和 P 层,V 层还是可以让各端实现,当然如果强行在 KMM模块实现也是可以的。
但是现在 KMM 还不够成熟,也存在一些未知问题,不过我决定 开始大胆在项目中使用 。
KMM 入门简介与基本环境搭建
文章目录
什么是KMM?
KMM 全称:Kotlin Multiplatform Mobile,是基于 Kotlin 语言进行多平台开发的一套技术框架,它和 Kotlin Native(简称 KN)有一定联系,但 KMM 主要面相移动端开发,即:Android、iOS、Web,而 KN 则主要面相 Linux、macOS、Windows 等
当然,KMM 在 iOS 平台的实现,离不开 Kotlin Native,Kotlin 代码最终会在 iOS 工程中生成一套 Framework 库,可供 Objective-C、Swift 进行调用
KMM 宗旨是使用 Kotlin 语言和技术栈,开发一套可以在多平台之间共享的代码库,用来构建统一的代码逻辑,而不用针对各个平台都去实现自己的一套,从而导致人力的浪费
这里引用 Kotlin 官网的一张图来说明 Kotlin 多平台的工作原理
Kotlin Mutiplatform 之间的关系
Kotlin 官方开发的多平台框架分为以下几种:
-
标准 Kotlin(Kotlin Stdlib)
即 Kotlin JVM,由于 Kotlin 最初是基于 JVM 运行的,所以可以使用 Java 的全部功能,同时还能支持 Kotlin 特有的各种语法糖
-
Kotlin Native
简称 KN,内部对各平台(如:Windows、Linux、macOS、iOS、Android)Native API(不使用 Runtime 的)进行封装,底层使用 LLVM 进行编译,可以使用 Kotlin 调用各平台特定的 API 或基于一些 C/C++ 库的能力,如:OpenGL、OpenCV 等,使多平台共享一套 Kotlin 代码
-
Kotlin JS
基本原理是将 Kotlin 代码翻译成 JavaScript,同时可以调用一些 JavaScript 特定的接口,从而进行 Web 开发,Kotlin JS 在功能和热度上远不及 TypeScript 这样的语言,后续发展方向目前尚不明确
几种框架的联系如下图所示:
与其他跨平台框架的简单对比
KMM 与 Flutter 的基本思路差异
与 Flutter 这种框架的思想相反,KMM 是用一套语言生成多个平台特定的字节码,所有的翻译工作由 kotlinc 或 kotlin-nativec 编译器来执行,从某种角度来讲,是『从上到下』,而 Flutter 的思想是『从下到上』,这也决定了两种框架适用的场景,Flutter 就适合绘制 UI,而 KMM 则是更适合与 UI 无关的逻辑代码,比如:Model 层,网络请求、数据解析、建模等
成本差异
-
体积:
-
使用 Flutter 需要在 App 包内部增加两个引擎:
-
一个是 Flutter 的渲染引擎,该引擎使用 C/C++ 开发,直接调用 OpenGL/Skia 的 API 进行绘制,从而摆脱 iOS 的 UIKit 以及 Android 的 View 组件直接渲染成需要的样式,从保证样式高度统一
-
另一个是 Dart 语言的 Runtime,用于解析并运行 Dart 语言编译的 Bundle
这两者减小了开发者的适配成本,但增大了 APP 的包体积(其他类似的跨平台框架,如:React Native 等,也会内置 JavaScript Core 或 V8 引擎)
-
-
KMM 针对不同平台生成不同的二进制依赖包,根本上还是调用了 Android、iOS 的原生 API,并不会内置引擎这类文件,对 App 的体积影响相对较小,同时也保证了性能
-
-
技术栈:
-
Flutter 使用 Dart 开发,无论是 Web 开发者,还是原生 App 开发者,都需要抽时间去学习一门新的语言,理解新的开发模式,虽然 Dart 与 JavaScript、Java 有着类似之处,且开发形式和 React 相近,但仍有一定学习门槛
-
Kotlin 已经成为 Google 官方主推的 Android 开发语言(https://developer.android.google.cn/kotlin/first),且由于 Kotlin 与 Java 交互非常方便,目前很多 Android 开发者已经完全切换到 Kotlin 来进行 App 开发,很多与平台无关的工具类、算法、数据模型可以直接利用 KMM 实现跨平台,与 Flutter 相比,至少 Android 开发者的门槛要求较低
-
-
风险点:
- 众所周知,App Store 对 App 的审核一直都是极为严格的,JSPatch、React Native 等框架的使用都有过审核被拒的情况,从某种角度来看,Flutter 与 Swift UI 在一定程度上目标相似,且绕开 iOS SDK 的 UIKit,Apple 虽没有明确对 Flutter 表态,但按照 Apple 的风格,Flutter 在未来仍存在一定的被拒风险
- KMM 会将 Kotlin 代码编译为标准的 Apple Framework,在不引入其他第三方库的情况下,不存在调用高风险 API 的情况,故对 App Store 审核的影响较小,风险较低
-
适用场景:
-
由于 Flutter 才用类似 3D 游戏的渲染理念,统一了界面渲染引擎,利用 Dart 可以高度保证双端样式和交互逻辑一致,且几乎不存在界面适配问题,完全抹平了 TextView 和 UILabel 这类控件之间的差异,所以 Flutter 适合于界面构建
-
而 KMM 并不适合 UI,双端的组件,生命周期、API 差异都比较大,KMM 在技术上可以实现功能,但相当于写了两份代码,失去了意义
这里翻译一把官方的建议:
-
架构层级 | 是否推荐使用共享代码 |
---|---|
业务逻辑层 | 推荐 |
平台数据访问 | 可选,但需要调用平台特定的代码,行为可以共享 |
前端交互(输入、通信等) | 可选,可以考虑使用 MVI(Model-View-Intent,MVP 模式的衍生) 进行解耦,共享控制层代码 |
UI(包括动画、转场等) | 强烈不推荐,应该使用平台特定的代码 |
其他业界类似框架
-
Xamarin
组织:Microsoft
开发语言:C#
基于 .NET Core 的跨平台开发框架,与 KMM 部分思想一致,适合有 WPF 或 UWP App 开发经验的开发者,需要理解 .NET 的开发模式,且复用现有代码逻辑比较困难,优点是对性能影响较小
-
Cordova
组织:Apache 基金会
开发语言:HTML5、 JavaScript
本质是在一个 App 中运行优化过的 H5 页面,同时对一些 API 进行封装,可使用 JavaScript 调用,性能较差,和 KMM 思想相反
-
React Native
组织:Facebook
开发语言:JavaScript
使用 JavaScript 调用原生 API 和控件,相对于 Cordova,性能有大幅提升,但受制于 React Native 框架的封装,很多能力无法调用,需要双端开发一系列 API,双端差异也比较大,有时候工作量反而增大,优点是对 Web 开发人员比较友好
跑一个 KMM Demo
-
需要的工具:
- Android Studio(4.2 版本以上,需要安装 KMM 插件)
- Xcode(最新即可)
- JDK(8 及以上)
-
其他参考资料:
-
Kotlin 官网环境配置文档:https://kotlinlang.org/docs/mobile/setup.html
-
KMM 插件:https://plugins.jetbrains.com/plugin/14936-kotlin-multiplatform-mobile
-
安装完需要的工具、插件以后,打开 Android Studio,新建一个项目,即可选择新建 KMM 工程
完成基本信息填写以后,可以选择是否使用 Cocoapods 来进行依赖 iOS 平台的依赖管理,如果不需要就选成『Regular Framework』
**注意:**使用 KMM Plugin 建立的工程,会默认使用 Kotlin(.kts 文件)的形式来进行 Gradle 配置,另外,其新建的 iOS 工程,也默认使用 Swift UI 进行开发,且这两项不可以配置,如果需要使用 Groovy,或者使用传统的 iOS UI 开发形式,需要以集成的形式来新建 KMM Module
工程创建完成后,在 Android Studio 顶部工具栏中,即可选择在 Android 或 iOS 设备(含模拟器)上运行
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-PXqPB915-1622083003193)(https://img.coderyuan.com/1622035115359.png)]
如果需要在 iOS 设备上运行,KMM 模块会利用 Gradle 插件,自动调用 Xcode 进行构建,并调起 iOS 模拟器运行
KMM 工程文件结构
最后附上由 KMM 插件建立的 KMM 工程,默认的文件目录结构说明
├── androidApp # 实际 Android APP Module
├── build.gradle.kts # 工程根 Gradle 配置
├── gradle
├── gradle.properties
├── gradlew
├── gradlew.bat
├── iosApp # 实际的 iOS 工程根目录
├── local.properties
├── settings.gradle.kts
└── shared # KMM 模块代码目录
├── build.gradle.kts # KMM 模块 Gradle 配置(依赖、插件、构建 Task、cinterop 等配置)
└── src # 内部模块形式都为 Gradle 工程 Module
├── androidMain # Android 差异化代码,最终生成 AAR
├── commonMain # 共享模块 API 代码
├── iosMain # iOS 差异化代码,
└── nativeInterop # 默认不会创建,用来存放 *.def 文件,描述与 C/C++ 代码,或 Apple Framework 交互时,构建 klib 的配置
以上是关于不学Flutter,我们来用Kotlin KMM跨平台吧的主要内容,如果未能解决你的问题,请参考以下文章
一文快速带您了解 KMMCompose 和 Flutter 的现状 | 开发者说·DTalk