android 与 flutter 之间的通信

文章目录

  • 前言
  • 集成 flutter 混合开发
  • android 与 flutter 之间的通信
  • 总结
一、前言

因为flutter 具有跨平台的属性,既可以在android上跑,也能在ios 上跑,所以为了节约开发的成本,减少人力,势必就会用到它。然而已有的项目部不太可能重新写,所以就需要进行混合开发。也就是在原生中集成flutter,进行混合开发。混合开发就会遇到原生和flutter的通信问题,今个就讲讲原生和flutter的通信。

二、首先创建个flutter module,然后集成到app中

1、在原生项目的父目录下,使用命令,创建flutter项目:
flutter create -t module --org com.example flutter_demo
在这里插入图片描述
创建完毕,然后我们用as打开这个父目录,可以看到我们的flutter_demo 已经创建好了,如图:
在这里插入图片描述
2、在原生app里面的settings.gradle,include ‘:app’ 下面添加:

setBinding(new Binding([gradle: this]))
evaluate(new File(settingsDir.parentFile,'flutter_demo/.android/include_flutter.groovy'
))
include ':flutter_demo'

3、在原生app下的build.gradle中添加依赖:

dependencies {//...implementation project(':flutter')
}

添加完毕,我们切回 app的项目,运行会发现报错了。
在这里插入图片描述
报错是说flutterPlugin 没法用,这里在settings.gradle 将repositoriesMode改为:RepositoriesMode.PREFER_PROJECT。重新运行。
如果还遇到第三方解析失败,添加maven:

dependencyResolutionManagement {repositoriesMode.set(RepositoriesMode.PREFER_PROJECT)repositories {maven { url 'https://jitpack.io' }maven { url 'https://maven.aliyun.com/nexus/content/groups/public/' }maven { url 'https://maven.aliyun.com/repository/central' }maven { url 'https://maven.aliyun.com/nexus/content/repositories/google' }google()mavenCentral()}
}

另外在项目的build.gradel 添加:

allprojects {repositories {maven { url 'https://jitpack.io' }maven { url 'https://maven.aliyun.com/nexus/content/groups/public/' }maven { url 'https://maven.aliyun.com/repository/central' }maven { url 'https://maven.aliyun.com/nexus/content/repositories/google' }google()mavenCentral()}
}

然后运行app,就可以了。如果你还有其他报错,切换到根目录,去检查下flutter_demo里头的这两个文件。打开main.dart,提示你Enable Dart support,点击它就可以。然后再打开 pubspec.yaml ,点击pub get 获取相应的依赖。确保flutter项目的环境和依赖库没问题。

到这里,我们的flutter_demo 就集成到我们的app中了。接下来就是看android和flutter的通信

三、android和flutter的通信

上面的项目,每次要看flutter代码是不是每次都要切过来切过去的,所以呢,我们可以在setting.gradle 加上这么一行代码:
project(‘:flutter_demo’).projectDir = new File(‘…/flutter_demo’)
在这里插入图片描述
这样,我们在app的项目中就能查看flutter的代码了。好了,我们最想知道的就是android 怎么打开 flutter页面。接这往下看。

1、android 跳转 flutter:
在清单AndroidManifest里面添加 FlutterActivity

    <activity android:name="io.flutter.embedding.android.FlutterActivity"android:configChanges="orientation|keyboardHidden|keyboard|screenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"android:hardwareAccelerated="true"android:windowSoftInputMode="adjustResize"></activity>

点击跳转:

   binding.fab.setOnClickListener { view ->//跳转flutterstartActivity(FlutterActivity.createDefaultIntent(this))}

你会发现跳转很慢,所以,我们用带有缓存引擎的初始路由来启动FlutterActivity
创建一个MyApplication 然后 在onCreate 中进行缓存引擎的初始化。

    // 创建一个Flutter引擎flutterEngine = new FlutterEngine(this);// 开始执行 Dart 代码来预热flutter引擎flutterEngine.getDartExecutor().executeDartEntrypoint(DartExecutor.DartEntrypoint.createDefault());//缓存Flutter引擎用来开启FlutterActivityFlutterEngineCache.getInstance().put("my_engine_id", flutterEngine);}

这个我们就能使用缓存引擎跳转Flutter。

 binding.fab.setOnClickListener { view ->//跳转flutterstartActivity(FlutterActivity.withCachedEngine("my_engine_id").build(this));}

很明显立马就跳转过去了。

2、如何跳转不同的flutter页面?
在applation 的onCreate 初始化需要跳转的页面, 到我们的Application 中的onCreate添加:

flutterEngine.getNavigationChannel().setInitialRoute("/test2");

然后修改main.dart 的代码:

void main() => runApp(_widgetForRoute(window.defaultRouteName));Widget _widgetForRoute(String route) {
switch (route) {case '/test1':return const Test1();case '/test2':return const Test2();case '/test3':return const Test3();default:return const Test1();
}
}

Test1是Test1.dart,代表不同的页面。当我们要跳转不同的页面,只要修改
flutterEngine.getNavigationChannel().setInitialRoute(“/test2”);就可以了,比如我们要跳转到Test3页面改成 flutterEngine.getNavigationChannel().setInitialRoute(“/test3”);
这个很简单,根据不同的标识,跳转对应的页面就行了。

四、接下来,就是文章的主题,讲通信方式都有哪些?

BasicMsgChannel
EventChannel
MethodChannel

1、BasicMsgChannel 方式
双向的,原生可以给flutter发送,然后flutter同时也可以返回信息给原生

发送:

    val flutterEngine = MyApplication.flutterEngineval basicMessageChannel = BasicMessageChannel(flutterEngine.dartExecutor.binaryMessenger,"basicMessageChannel",StringCodec.INSTANCE)basicMessageChannel.send("通过basicMessageChannel发送消息"){message: String?->Log.d("ssz", "接收:$message") //message 是flutter发回给原生的消息}

flutter 接收:

_basicMessageChannel = const BasicMessageChannel('basicMessageChannel', StringCodec());_basicMessageChannel.setMessageHandler((String? message) => Future<String>((){setState(() {//刷新控件_basicMessage = "flutter接收了消息:${message!}";});return "flutter 收到了";//这里是返回信息给原生}));

我们也可以反过来,原生接收,flutter发送,如下:
原生接收:

    basicMessageChannel.setMessageHandler { message, reply ->Log.d("ssz", "接收:$message")}

flutter 发送:

      _basicMessageChannel.send("我是flutter的消息");

2、MethodChannel 方法
主要是flutter 调用原生

原生接收:

val methodChannel = MethodChannel(flutterEngine.dartExecutor.binaryMessenger, "test2")binding.btnTest2.setOnClickListener {toFlutter()methodChannel.setMethodCallHandler { call, result ->if (call.method.equals("open")){Log.d("ssz", "接收flutter调用")}}}

flutter 发送

 const _methodChannel = MethodChannel('test2');_methodChannel.invokeListMethod("open");

3、EventChannel方法
主要是原生发送给flutter,这个方法使用不当就会接受不到,谨慎使用。

原生发送:

 val eventChannel = EventChannel(MyApplication.flutterEngine.dartExecutor.binaryMessenger, "test3")binding.btnTest3.setOnClickListener {toFlutter()eventChannel.setStreamHandler(object : StreamHandler{override fun onListen(arguments: Any?, events: EventSink?) {Log.d("ssz","执行了 onListen");events?.success("原生发送")}override fun onCancel(arguments: Any?) {}})}}

flutter 接收

void initState() {super.initState();Future.delayed(const Duration(milliseconds: 6000), () {//需要做个延迟,不然原生onListen会不执行,导致不能发送消息var eventChannel = const EventChannel("test3");eventChannel.receiveBroadcastStream().listen((dynamic event) {setState(() {_EventMessage = "flutter接收$event";});}, onError: (dynamic error){setState(() {_EventMessage = "flutter接收$error";});},cancelOnError: true);});}

最后呢,关于路由方面,有的业务可能需要跳转很多不同的页面,原生的方式不太友好,可以选择闲鱼开源的库 https://github.com/alibaba/flutter_boost ,提高开发的效率。

以上代码地址:https://github.com/shenshizhong/HybridFlutter

总结

总的来讲:
1、android集成flutter,进行混合开发
2、android 与 flutter 的通信
3、使用第三方提高开发效率

如果对你有一点点帮助,那是值得高兴的事情。:)
我的csdn:http://blog.csdn.net/shenshizhong
我的简书:http://www.jianshu.com/u/345daf0211ad

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/104284.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Matlab地理信息绘图—数据诊断

文章目录 数据诊断分析&#xff08;均值方差&#xff09;Matlab代码实现结果展示 数据诊断分析&#xff08;均值方差&#xff09; 均值方差检测是一种简单但有效的异常检测方法&#xff0c;主要基于样本的均值和方差的统计信息。该方法的核心思想是假设正常的样本点应该聚集在…

CNN-generated images are surprisingly easy to spot... for now

CNN-generated images are surprisingly easy to spot… for now----《目前CNN生成的图像非常容易被发现》 背景&#xff1a; 研究者们发现&#xff0c;仅仅对一种由CNN模型生成的图像进行训练的分类器&#xff0c;也可以检测许多其他模型生成的结果。由此提出这样的观点&#…

C语言中的自定义类型详解(结构体 + 枚举 + 联合(共用体))

文章目录 1. 结构体1.1 结构体的声明1.2 结构体成员的访问1.3 匿名结构体1.4 结构体的自引用1.5 结构体内存对齐&#xff08;计算结构体的大小&#xff09;1.6 结构体传参1.6.1 传值传递1.6.2 传址传递&#xff08;使用指针&#xff09; 2. 位段2.1 什么是位段&#xff1f;2.2 …

铅华洗尽,粉黛不施,人工智能AI基于ProPainter技术去除图片以及视频水印(Python3.10)

视频以及图片修复技术是一项具有挑战性的AI视觉任务&#xff0c;它涉及在视频或者图片序列中填补缺失或损坏的区域&#xff0c;同时保持空间和时间的连贯性。该技术在视频补全、对象移除、视频恢复等领域有广泛应用。近年来&#xff0c;两种突出的方案在视频修复中崭露头角&…

miRNA测序数据生信分析——第四讲,未知物种的生信分析实例

miRNA测序数据生信分析——第四讲&#xff0c;未知物种的生信分析实例 miRNA测序数据生信分析——第四讲&#xff0c;未知物种的生信分析实例1. 下载测序数据2. 原始数据质控——软件fastqc3. 注释tRNA和rRNA&#xff0c;使用Rfam数据库——软件blast&#xff0c;Rfam_statisti…

监控系列(六)prometheus监控DMHS操作步骤

一、监控的操作逻辑 给操作系统安装expect命令expect脚本执行dmhs_console脚本执行 cpt / exec 命令用脚本进行过滤字符串过滤dm_export读取脚本与当前日期作比较&#xff0c;然后返回差值 二、安装步骤 1. linux中Expect工具的安装及使用方法 https://blog.csdn.net/wangta…

mybatis拦截器源码分析

mybatis拦截器源码分析 拦截器简介 mybatis Plugins 拦截器由于Mybatis对数据库访问与操作进行了深度的封装,让我们应用开发效率大大提高,但是灵活度很差拦截器的作用:深度定制Mybatis的开发抛出一个需求 :获取Mybatis在开发过程中执行的SQL语句(执行什么操作获取那条SQL语句…

ChatGPT,AIGC 制作按年份选择的动态条形图

在数据分析与可视化中,条形图是用来进行对比分析,在正负条形图中都有哪些好处与优点呢? 正负条形图是一种常用的数据可视化方式,它的优点和好处包括: 1.明确展示:正负条形图可以清晰地显示出数据中的正负差异,使读者能直观地看出数据的变化和趋势。 2.直观比较:正负条…

苹果电脑其他内存怎么清理?

苹果电脑中的应用程序大部分是可以通过将其拖拽至废纸篓并倾倒来卸载的。但是部分程序在卸载后仍有残留文件&#xff0c;比如support文件和pref设置等文件的。小编今天介绍下苹果电脑清理内存怎么清理卸载残留以及好用的清理技巧分享。 一、苹果电脑清理内存怎么清理 苹果电脑…

简单实现一个todoList(上移、下移、置顶、置底)

演示 html部分 <!DOCTYPE html> <html> <head><title>表格示例</title> </head> <body><table border"1"><thead><tr><th>更新时间</th><th>操作</th></tr></thead…

thinkphp5.1 获取缓存cache(‘cache_name‘)特别慢,php 7.0 unserialize 特别慢

thinkphp5.1 获取缓存cache(‘cache_name’)特别慢&#xff0c;php 7.0 unserialize 特别慢 场景&#xff1a; 项目中大量使用了缓存&#xff0c;本地运行非常快&#xff0c;二三百毫秒&#xff0c;部署到服务器后 一个表格请求就七八秒&#xff0c;最初猜想是数据库查询慢&am…

KY258 日期累加

KY258 日期累加 int main() {int n 0; //样例个数cin >> n;//for循环处理n个样例for (int i 0; i < n; i){int y, m, d, num;int days[12] { 31,28,31,30,31,30,31,31,30,31,30,31 };//输入年月日 要加的天数cin >> y >> m >> d >>…

完整教程:Java+Vue+Websocket实现OSS文件上传进度条功能

引言 文件上传是Web应用开发中常见的需求之一&#xff0c;而实时显示文件上传的进度条可以提升用户体验。本教程将介绍如何使用Java后端和Vue前端实现文件上传进度条功能&#xff0c;借助阿里云的OSS服务进行文件上传。 技术栈 后端&#xff1a;Java、Spring Boot 、WebSock…

【Java学习之道】GUI开发的基本概念

引言 在这一章&#xff0c;我们将一起走进Java的图形用户界面&#xff08;GUI&#xff09;开发的世界。在你阅读完这篇文章后&#xff0c;你将能够了解什么是GUI&#xff0c;以及如何使用Java进行GUI的开发。 一、什么是GUI 首先&#xff0c;让我们来解答一个许多初学者都会…

AN基础工具——变形工具

【AN基础工具——变形工具】 基本使用方法&#xff1a;任意变形工具基础动画 本篇内容&#xff1a;学会使用变形工具 重点内容&#xff1a;变形工具 工 具&#xff1a;Adobe Animate 2022 基本使用方法&#xff1a; 任意变形工具 《任意变形工具&#xff08;快捷键Q&#xff0…

深度学习系列51:hugging face加速库optimum

1. 普通模型 Optimum是huggingface transformers库的一个扩展包&#xff0c;用来提升模型在指定硬件上的训练和推理性能。Optimum支持多种硬件&#xff0c;不同硬件下的安卓方式如下&#xff1a; 如果是国内安装的话&#xff0c;记得加上-i https://pypi.tuna.tsinghua.edu.c…

八大排序算法(含时间复杂度、空间复杂度、算法稳定性)

文章目录 八大排序算法(含时间复杂度、空间复杂度、算法稳定性)1、&#xff08;直接&#xff09;插入排序1.1、算法思想1.2、排序过程图解1.3、排序代码 2、希尔排序3、冒泡排序3.1、算法思想3.2、排序过程图解3.3、排序代码 4、&#xff08;简单&#xff09;选择排序4.1、算法…

Springcloud笔记(2)-Eureka服务注册中心

Eureka服务注册 Eureka作为一个微服务的治理中心&#xff0c;它是一个服务应用&#xff0c;可以接收其他服务的注册&#xff0c;也可以发现和治理服务实例。 服务治理中心是微服务&#xff08;分布式&#xff09;架构中最基础和最核心的功能组件&#xff0c;它主要对各个服务…

kafka生产者发送消息报错 Bootstrap broker localhost:9092 (id: -1 rack: null) disconnected

报这个错误是因为kafka里的配置要修改下 在config目录下 server.properties配置文件 这下发送消息就不会一直等待&#xff0c;就可以发送成功了

CTFHub SSRF 题目

文章目录 CTFHub SSRF 通关教程1. 内网访问&#xff0c;伪协议利用1.1 内网访问1.2 伪协议读取文件1.3 端口扫描 2. POST请求&#xff0c;上传文件&#xff0c;FastCGI协议&#xff0c;Redis协议2.1 POST请求2.2 上传文件2.3 FastCGI协议2.4 Redis协议 3. Bypass系列3.1 URL By…