Flutter和Native 通信 android端

简介: Flutter和Native 通信 android端

通信用到的类

  1. MethodChannel
  2. EventChannel
  3. BasicMessageChannel
MethodChannel使用方式(flutter 调用原生方法)
1. 原生代码
  1. 定义通信标识
   private val METHOD_CHANNEL = "tip.flutter.io/method"
  1. 创建对象
 MethodChannel((getView() as FlutterView), METHOD_CHANNEL).setMethodCallHandler { call, result ->
           if (call.method == "getBatteryLevel") {
               val ba = getBatteryLevel()
               if (ba != -1) {
                   result.success(ba)
               } else {
                   result.error("UNAVAILABLE", "Battery level not available.", null)
               }
           } else {
               result.notImplemented()
           }
       }
  1. 定义原生方法
  private fun getBatteryLevel(): Int {
        return 123
    }
2. dart代码
  1. 创建对象
  static const platfrom = const MethodChannel("tip.flutter.io/method");
  1. 初始化方法
 Future<Null> _getBatteryLevel() async {
    String batteryLevel;
    try {
      final int result = await platfrom.invokeMethod("getBatteryLevel");
      batteryLevel = 'Battery level at $result % .';
    } on PlatformException catch (e) {
      batteryLevel = "Failed to get battery level: '${e.message}'.";
    }
    setState(() {
      _batteryLevel = batteryLevel;
    });
  }
  1. 调用方法
 @override
  void initState() {
    // TODO: implement initState
    _getBatteryLevel();
    super.initState();
  }
EventChannel使用方式(主要是native向flutter主动推送数据,例如推送电量,网络状态)
BasicMessageChannel使用方式(native->flutter,flutter->native)
完整nativie 代码如下
package com.gctech.nativeandflutter

import android.os.Bundle
import android.os.Handler
import android.view.View
import android.widget.Toast
import io.flutter.facade.FlutterFragment
import io.flutter.plugin.common.BasicMessageChannel
import io.flutter.plugin.common.EventChannel
import io.flutter.plugin.common.MethodChannel
import io.flutter.plugin.common.StringCodec
import io.flutter.view.FlutterView
import java.util.*

/**
 *    author: yu.jl
 *    e-mail: bbfx89625@gmail.com
 *    time  : 2019/7/24
 *    desc  :
 */
class FlutterBaseFragment : FlutterFragment() {
    private val METHOD_CHANNEL = "tip.flutter.io/method"
    private val EVENT_CHANNEL = "tip.flutter.io/event"
    private val MESSAGE_CHANNEL = "tip.flutter.io/message"
    private val handler = Handler()
    var mesageChan: BasicMessageChannel<String>? = null

    companion object {
        fun newInstance(router: String) = FlutterBaseFragment().apply {
            arguments = Bundle().apply {
                putString("router", router)
            }

        }
    }

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        MethodChannel((getView() as FlutterView), METHOD_CHANNEL).setMethodCallHandler { call, result ->
            if (call.method == "getBatteryLevel") {
                val ba = getBatteryLevel()
                if (ba != -1) {
                    result.success(ba)
                } else {
                    result.error("UNAVAILABLE", "Battery level not available.", null)
                }
            } else {
                result.notImplemented()
            }
        }
        EventChannel((getView() as FlutterView), EVENT_CHANNEL).setStreamHandler(object : EventChannel.StreamHandler {
            override fun onListen(arguments: Any?, events: EventChannel.EventSink?) {
                Timer().schedule(object : TimerTask() {
                    override fun run() {
                        handler.post {
                            events?.success("当前时间毫秒${System.currentTimeMillis()}")
                        }
                    }
                }, 1000, 1000)
            }

            override fun onCancel(p0: Any?) {
            }

        })
        mesageChan = BasicMessageChannel<String>(
            (getView() as FlutterView),
            MESSAGE_CHANNEL,
            StringCodec.INSTANCE
        )
        mesageChan?.setMessageHandler { a, b ->
            b.reply("aaaa${System.currentTimeMillis()}")
            Toast.makeText(context,a,Toast.LENGTH_LONG).show()
           // Log.e("收到消息", "a=$a=b=${b.reply("aaaa${System.currentTimeMillis()}")}")
        }
    }
    private fun getBatteryLevel(): Int {
        return 123
    }


}
完整dart 代码如下
import 'dart:async';

import 'package:flutter/material.dart';
import 'package:flutter/services.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: MyHomePage(title: 'Flutter Demo Home Page'),
    );
  }
}

class MyHomePage extends StatefulWidget {
  MyHomePage({Key key, this.title}) : super(key: key);
  
  final String title;

  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  int _counter = 0;
  String _batteryLevel = '';
  String _eventStr = '';
  String _mssageStr = '_mssageStr';
  static const platfrom = const MethodChannel("tip.flutter.io/method");
  static const eventChannel = const EventChannel("tip.flutter.io/event");
  static const messageChannel = const BasicMessageChannel<String>(
      "tip.flutter.io/message", StringCodec());
  StreamSubscription _streamSubscripton;

  void _incrementCounter() {
    setState(() {
      _counter++;
    });
  }

  Future<Null> _getBatteryLevel() async {
    String batteryLevel;
    try {
      final int result = await platfrom.invokeMethod("getBatteryLevel");
      batteryLevel = 'Battery level at $result % .';
    } on PlatformException catch (e) {
      batteryLevel = "Failed to get battery level: '${e.message}'.";
    }
    setState(() {
      _batteryLevel = batteryLevel;
    });
  }

  Future<Null> _msssage() async {
    messageChannel.setMessageHandler((String message) => Future<String>(() {
          print("收到native的消息$message");
          setState(() {
            _mssageStr = message;
          });
          return "收到native的消息$message";
        }));
    String ponse;
    try {
      ponse = await messageChannel.send("我来自flutter");
    } catch (e) {
      print(e);
    }
    setState(() {
      _mssageStr = ponse;
    });
    print(ponse);
  }

  Future<Null> _lisEvent() async {
    String eventStr;
    try {
      _streamSubscripton = eventChannel
          .receiveBroadcastStream()
          .listen(_onToDart, onError: _onToDartError);
    } on PlatformException catch (e) {
      eventStr = "event get data err: '${e.message}'.";
      setState(() {
        _eventStr = eventStr;
      });
    }
  }

  @override
  void dispose() {
    if (_streamSubscripton != null) {
      _streamSubscripton.cancel();
      _streamSubscripton = null;
    }

    // TODO: implement dispose
    super.dispose();
  }

  _onToDart(message) {
    setState(() {
      _eventStr = message;
    });
    print(message);
  }

  _onToDartError(error) {
    print(error);
  }

  @override
  void initState() {
    // TODO: implement initState
    _getBatteryLevel();
    _lisEvent();
    _msssage();
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
   
    return Scaffold(
      appBar: AppBar(
        
        title: Text(widget.title),
      ),
      body: Center(
        
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: <Widget>[
            Text(
              'AAA You have pushed the button this many times:',
            ),
            Text(
              '$_counter',
              style: Theme.of(context).textTheme.display1,
            ),
            Text(
              '$_batteryLevel',
            ),
            Text(
              '$_eventStr',
            ),
            Text(
              '$_mssageStr',
            ),
          ],
        ),
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: _incrementCounter,
        tooltip: 'Increment',
        child: Icon(Icons.add),
      ), // This trailing comma makes auto-formatting nicer for build methods.
    );
  }
}

c盘
  1. 修改.gradle 目录
    在Windows的环境变量中新建一个环境变量设置,GRADLE_USER_HOME,值为D:\Users\shaowei.gradle,设置完成之后,点击确定,关闭设置窗口。这个时候可以去AS中看下gradle的用户目录,自动变成了环境变量中的值了
  2. 修改配置文件Pixel_3_XL_API_28.ini
    avd.ini.encoding=UTF-8
    path=D:\avd\Pixel_3_XL_API_28.avd
    path.rel=avd\Pixel_3_XL_API_28.avd
    target=android-28


    相关文章
    |
    1月前
    |
    前端开发 Java 编译器
    当flutter react native 等混开框架-并且用vscode-idea等编译器无法打包apk,打包安卓不成功怎么办-直接用android studio如何打包安卓apk -重要-优雅草卓伊凡
    当flutter react native 等混开框架-并且用vscode-idea等编译器无法打包apk,打包安卓不成功怎么办-直接用android studio如何打包安卓apk -重要-优雅草卓伊凡
    82 36
    当flutter react native 等混开框架-并且用vscode-idea等编译器无法打包apk,打包安卓不成功怎么办-直接用android studio如何打包安卓apk -重要-优雅草卓伊凡
    |
    22天前
    |
    缓存 Java 测试技术
    【01】噩梦终结flutter配安卓android鸿蒙harmonyOS 以及next调试环境配鸿蒙和ios真机调试环境-flutter项目安卓环境配置-gradle-agp-ndkVersion模拟器运行真机测试环境-本地环境搭建-如何快速搭建android本地运行环境-优雅草卓伊凡-很多人在这步就被难倒了
    【01】噩梦终结flutter配安卓android鸿蒙harmonyOS 以及next调试环境配鸿蒙和ios真机调试环境-flutter项目安卓环境配置-gradle-agp-ndkVersion模拟器运行真机测试环境-本地环境搭建-如何快速搭建android本地运行环境-优雅草卓伊凡-很多人在这步就被难倒了
    155 3
    【01】噩梦终结flutter配安卓android鸿蒙harmonyOS 以及next调试环境配鸿蒙和ios真机调试环境-flutter项目安卓环境配置-gradle-agp-ndkVersion模拟器运行真机测试环境-本地环境搭建-如何快速搭建android本地运行环境-优雅草卓伊凡-很多人在这步就被难倒了
    |
    1月前
    |
    前端开发 Java Shell
    【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
    【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
    177 20
    【08】flutter完成屏幕适配-重建Android,增加GetX路由,屏幕适配,基础导航栏-多版本SDK以及gradle造成的关于fvm的使用(flutter version manage)-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
    |
    1月前
    |
    Dart 前端开发 Android开发
    【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
    【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
    54 4
    【09】flutter首页进行了完善-采用android studio 进行真机调试开发-增加了直播间列表和短视频人物列表-增加了用户中心-卓伊凡换人优雅草Alex-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草Alex
    |
    2月前
    |
    Dart 前端开发 Android开发
    【02】写一个注册页面以及配置打包选项打包安卓apk测试—开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
    【02】写一个注册页面以及配置打包选项打包安卓apk测试—开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
    43 1
    【02】写一个注册页面以及配置打包选项打包安卓apk测试—开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程-商业应用级实战开发-优雅草央千澈
    |
    4月前
    |
    开发框架 Dart Android开发
    安卓与iOS的跨平台开发:Flutter框架深度解析
    在移动应用开发的海洋中,Flutter作为一艘灵活的帆船,正引领着开发者们驶向跨平台开发的新纪元。本文将揭开Flutter神秘的面纱,从其架构到核心特性,再到实际应用案例,我们将一同探索这个由谷歌打造的开源UI工具包如何让安卓与iOS应用开发变得更加高效而统一。你将看到,借助Flutter,打造精美、高性能的应用不再是难题,而是变成了一场创造性的旅程。
    |
    25天前
    |
    JavaScript 搜索推荐 Android开发
    【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
    【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
    64 8
    【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
    |
    2月前
    |
    缓存 前端开发 Android开发
    【04】flutter补打包流程的签名过程-APP安卓调试配置-结构化项目目录-完善注册相关页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程
    【04】flutter补打包流程的签名过程-APP安卓调试配置-结构化项目目录-完善注册相关页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程
    109 12
    【04】flutter补打包流程的签名过程-APP安卓调试配置-结构化项目目录-完善注册相关页面-开发完整的社交APP-前端客户端开发+数据联调|以优雅草商业项目为例做开发-flutter开发-全流程
    |
    21天前
    |
    安全 Android开发 iOS开发
    escrcpy:【技术党必看】Android开发,Escrcpy 让你无线投屏新体验!图形界面掌控 Android,30-120fps 超流畅!🔥
    escrcpy 是一款基于 Scrcpy 的开源项目,使用 Electron 构建,提供图形化界面来显示和控制 Android 设备。它支持 USB 和 Wi-Fi 连接,帧率可达 30-120fps,延迟低至 35-70ms,启动迅速且画质清晰。escrcpy 拥有丰富的功能,包括自动化任务、多设备管理、反向网络共享、批量操作等,无需注册账号或广告干扰。适用于游戏直播、办公协作和教育演示等多种场景,是一款轻量级、高性能的 Android 控制工具。

    热门文章

    最新文章

  1. 1
    flutter3-wetrip跨平台自研仿携程app预约酒店系统模板
  2. 2
    通过外部链接启动 Flutter App(详细介绍及示例)
  3. 3
    【Flutter 开发必备】AzListView 组件全解析,打造丝滑索引列表!
  4. 4
    Android历史版本与APK文件结构
  5. 5
    【01】噩梦终结flutter配安卓android鸿蒙harmonyOS 以及next调试环境配鸿蒙和ios真机调试环境-flutter项目安卓环境配置-gradle-agp-ndkVersion模拟器运行真机测试环境-本地环境搭建-如何快速搭建android本地运行环境-优雅草卓伊凡-很多人在这步就被难倒了
  6. 6
    【03】仿站技术之python技术,看完学会再也不用去购买收费工具了-修改整体页面做好安卓下载发给客户-并且开始提交网站公安备案-作为APP下载落地页文娱产品一定要备案-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
  7. 7
    【02】仿站技术之python技术,看完学会再也不用去购买收费工具了-本次找了小影-感觉页面很好看-本次是爬取vue需要用到Puppeteer库用node.js扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-优雅草卓伊凡
  8. 8
    Cellebrite UFED 4PC 7.71 (Windows) - Android 和 iOS 移动设备取证软件
  9. 9
    【01】仿站技术之python技术,看完学会再也不用去购买收费工具了-用python扒一个app下载落地页-包括安卓android下载(简单)-ios苹果plist下载(稍微麻烦一丢丢)-客户的麻将软件需要下载落地页并且要做搜索引擎推广-本文用python语言快速开发爬取落地页下载-优雅草卓伊凡
  10. 10
    【03】微信支付商户申请下户到配置完整流程-微信开放平台创建APP应用-填写上传基础资料-生成安卓证书-获取Apk签名-申请+配置完整流程-优雅草卓伊凡