PS小子不懂IOS开发,因此flutter插件系列文章只涉及Android
flutter本身SDK无法操作一些功能,必须借助安卓原生,如打开蓝牙,获取电量
一简单使用
我们仿照势力重写一个
Android层
package com.example.flutter_plugin0713
import android.telephony.ims.RegistrationManager
import androidx.annotation.NonNull
import io.flutter.embedding.engine.plugins.FlutterPlugin
import io.flutter.plugin.common.EventChannel
import io.flutter.plugin.common.EventChannel.StreamHandler
import io.flutter.plugin.common.MethodCall
import io.flutter.plugin.common.MethodChannel
import io.flutter.plugin.common.MethodChannel.MethodCallHandler
import io.flutter.plugin.common.MethodChannel.Result
import io.flutter.plugin.common.PluginRegistry
/** FlutterPlugin0713Plugin */
class FlutterPlugin0713Plugin : FlutterPlugin, MethodCallHandler {
/// The MethodChannel that will the communication between Flutter and native Android
///
/// This local reference serves to register the plugin with the Flutter Engine and unregister it
/// when the Flutter Engine is detached from the Activity
private lateinit var channel: MethodChannel
override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
channel = MethodChannel(flutterPluginBinding.binaryMessenger, "flutter_plugin0713")
channel.setMethodCallHandler(this)
}
override fun onMethodCall(@NonNull call: MethodCall, @NonNull result: Result) {
if (call.method == "getPlatformVersion") {
result.success("Android ${android.os.Build.VERSION.RELEASE}")
}else if(call.method == "getNative"){
result.success("Android 调用成功")
}
else {
result.notImplemented()
}
}
override fun onDetachedFromEngine(@NonNull binding: FlutterPlugin.FlutterPluginBinding) {
channel.setMethodCallHandler(null)
}
}
flutter层
import 'package:flutter/material.dart';
import 'dart:async';
import 'package:flutter/services.dart';
import 'package:flutter_plugin0713/flutter_plugin0713.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({Key? key}) : super(key: key);
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
String _platformVersion = 'Unknown';
@override
void initState() {
super.initState();
initPlatformState();
}
// Platform messages are asynchronous, so we initialize in an async method.
///调插件是一个异步的过程,你不知道插件什么时候返回
Future<void> initPlatformState() async {
String platformVersion;
// Platform messages may fail, so we use a try/catch PlatformException.
// We also handle the message potentially returning null.
try {
// platformVersion =
// await FlutterPlugin0713.platformVersion ?? 'Unknown platform version';
platformVersion =
await FlutterPlugin0713.getNative ?? '不知道是什么';
} on PlatformException {
platformVersion = 'Failed to get platform version.';
}
// If the widget was removed from the tree while the asynchronous platform
// message was in flight, we want to discard the reply rather than calling
// setState to update our non-existent appearance.
if (!mounted) return;
setState(() {
_platformVersion = platformVersion;
});
}
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('Plugin example app'),
),
body: Center(
child: Text('Running on: $_platformVersion\n'),
),
),
);
}
}
import 'dart:async';
import 'package:flutter/services.dart';
class FlutterPlugin0713 {
/// MethodChannel要指定一个ID,要和Android代码中的ID对应,以下是Android类FlutterPlugin0713Plugin的对应之处
/// override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
/// channel = MethodChannel(flutterPluginBinding.binaryMessenger, "flutter_plugin0713")
/// channel.setMethodCallHandler(this)
/// }
///
static const MethodChannel _channel = MethodChannel('flutter_plugin0713');
static Future<String?> get platformVersion async {
final String? version = await _channel.invokeMethod('getPlatformVersion');
return version;
}
static Future<String?> get getNative async {
final String? res = await _channel.invokeMethod('getNative');
return res;
}
}
运行试下
运行
二参数传递及返回
flutter代码
import 'package:flutter/material.dart';
import 'dart:async';
import 'package:flutter/services.dart';
import 'package:flutter_plugin0713/flutter_plugin0713.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({Key? key}) : super(key: key);
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
String _platformVersion = 'Unknown';
@override
void initState() {
super.initState();
initPlatformState();
}
///调插件是一个异步的过程,你不知道插件什么时候返回
Future<void> initPlatformState() async {
String platformVersion;
try {
// platformVersion =
// await FlutterPlugin0713.platformVersion ?? 'Unknown platform version';
platformVersion =
await FlutterPlugin0713.getNative ?? '不知道是什么';
} on PlatformException {
platformVersion = 'Failed to get platform version.';
}
if (!mounted) return;
setState(() {
_platformVersion = platformVersion;
});
}
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('Plugin example app'),
),
body: Center(
child: RaisedButton(
onPressed: (){
FlutterPlugin0713.sayHello("张欣爱我一生一世");
},
child: Text("参数传递"),
),
),
),
);
}
}
import 'dart:async';
import 'package:flutter/services.dart';
class FlutterPlugin0713 {
/// MethodChannel要指定一个ID,要和Android代码中的ID对应,以下是Android类FlutterPlugin0713Plugin的对应之处
/// override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
/// channel = MethodChannel(flutterPluginBinding.binaryMessenger, "flutter_plugin0713")
/// channel.setMethodCallHandler(this)
/// }
///
static const MethodChannel _channel = MethodChannel('flutter_plugin0713');
static Future<String?> get platformVersion async {
final String? version = await _channel.invokeMethod('getPlatformVersion');
return version;
}
static Future<String?> get getNative async {
final String? res = await _channel.invokeMethod('getNative');
return res;
}
static Future<String?> sayHello(String mesage) async {
//参数是键值对传递
final String? res = await _channel.invokeMethod('sayHello',<String,dynamic>{"abcdef":mesage});
return res;
}
}
Android 代码
package com.example.flutter_plugin0713
import android.telephony.ims.RegistrationManager
import android.util.Log
import androidx.annotation.NonNull
import io.flutter.embedding.engine.plugins.FlutterPlugin
import io.flutter.plugin.common.EventChannel
import io.flutter.plugin.common.EventChannel.StreamHandler
import io.flutter.plugin.common.MethodCall
import io.flutter.plugin.common.MethodChannel
import io.flutter.plugin.common.MethodChannel.MethodCallHandler
import io.flutter.plugin.common.MethodChannel.Result
import io.flutter.plugin.common.PluginRegistry
/** FlutterPlugin0713Plugin */
class FlutterPlugin0713Plugin : FlutterPlugin, MethodCallHandler {
/// The MethodChannel that will the communication between Flutter and native Android
///
/// This local reference serves to register the plugin with the Flutter Engine and unregister it
/// when the Flutter Engine is detached from the Activity
private lateinit var channel: MethodChannel
override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
channel = MethodChannel(flutterPluginBinding.binaryMessenger, "flutter_plugin0713")
channel.setMethodCallHandler(this)
}
override fun onMethodCall(@NonNull call: MethodCall, @NonNull result: Result) {
if (call.method == "getPlatformVersion") {
result.success("Android ${android.os.Build.VERSION.RELEASE}")
}else if(call.method == "getNative"){
result.success("Android 调用成功")
}else if(call.method == "sayHello"){
//获取flutter传递过来的参数
var message:String? = call.argument("abcdef")
Log.i("张欣",message?:"a")
result.success("Android 调用成功")
}
else {
result.notImplemented()
}
}
override fun onDetachedFromEngine(@NonNull binding: FlutterPlugin.FlutterPluginBinding) {
channel.setMethodCallHandler(null)
}
}
运行结果
3,使用Map传递参数
flutter层
import 'dart:async';
import 'package:flutter/services.dart';
class FlutterPlugin0713 {
/// MethodChannel要指定一个ID,要和Android代码中的ID对应,以下是Android类FlutterPlugin0713Plugin的对应之处
/// override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
/// channel = MethodChannel(flutterPluginBinding.binaryMessenger, "flutter_plugin0713")
/// channel.setMethodCallHandler(this)
/// }
///
static const MethodChannel _channel = MethodChannel('flutter_plugin0713');
static Future<String?> get platformVersion async {
final String? version = await _channel.invokeMethod('getPlatformVersion');
return version;
}
static Future<String?> get getNative async {
final String? res = await _channel.invokeMethod('getNative');
return res;
}
static Future<String?> sayHello(String mesage,String message2) async {
//参数是键值对传递
final Map<dynamic,dynamic> res = await _channel.invokeMethod('sayHello',<String,dynamic>{"abcdef":mesage,"qwer":message2});
String? resMessage = res['abcdef'];
String? info = res['info'];
print("张欣info的值是:$info");
return resMessage;
}
}
import 'package:flutter/material.dart';
import 'dart:async';
import 'package:flutter/services.dart';
import 'package:flutter_plugin0713/flutter_plugin0713.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({Key? key}) : super(key: key);
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
String _platformVersion = 'Unknown';
@override
void initState() {
super.initState();
initPlatformState();
}
///调插件是一个异步的过程,你不知道插件什么时候返回
Future<void> initPlatformState() async {
String platformVersion;
try {
// platformVersion =
// await FlutterPlugin0713.platformVersion ?? 'Unknown platform version';
platformVersion =
await FlutterPlugin0713.getNative ?? '不知道是什么';
} on PlatformException {
platformVersion = 'Failed to get platform version.';
}
if (!mounted) return;
setState(() {
_platformVersion = platformVersion;
});
}
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('Plugin example app'),
),
body: Center(
child: RaisedButton(
onPressed: () async{
String? message = await FlutterPlugin0713.sayHello("张欣爱我一生一世","第二个参数");
print("张欣flutter层:$message");
},
child: Text("参数传递"),
),
),
),
);
}
}
Android层代码,Android层我创建了两个辅助类
package com.example.flutter_plugin0713
import android.telephony.ims.RegistrationManager
import android.util.Log
import androidx.annotation.NonNull
import io.flutter.embedding.engine.plugins.FlutterPlugin
import io.flutter.plugin.common.EventChannel
import io.flutter.plugin.common.EventChannel.StreamHandler
import io.flutter.plugin.common.MethodCall
import io.flutter.plugin.common.MethodChannel
import io.flutter.plugin.common.MethodChannel.MethodCallHandler
import io.flutter.plugin.common.MethodChannel.Result
import io.flutter.plugin.common.PluginRegistry
/** FlutterPlugin0713Plugin */
class FlutterPlugin0713Plugin : FlutterPlugin, MethodCallHandler {
/// The MethodChannel that will the communication between Flutter and native Android
///
/// This local reference serves to register the plugin with the Flutter Engine and unregister it
/// when the Flutter Engine is detached from the Activity
private lateinit var channel: MethodChannel
override fun onAttachedToEngine(@NonNull flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
channel = MethodChannel(flutterPluginBinding.binaryMessenger, "flutter_plugin0713")
channel.setMethodCallHandler(this)
}
override fun onMethodCall(@NonNull call: MethodCall, @NonNull result: Result) {
if (call.method == "getPlatformVersion") {
result.success("Android ${android.os.Build.VERSION.RELEASE}")
}else if(call.method == "getNative"){
result.success("Android 调用成功")
}else if(call.method == "sayHello"){
//获取flutter传递过来的参数
var message:String? = call.argument("abcdef")
var info:String? = call.argument("qwer")
Log.i("张欣Android层","${message} ${info}")
//向flutter传递参数
var params = ConstraintsMap();
params.putString("abcdef","张欣爱我一生一世")
params.putString("info","随便写点东西")
result.success(params.toMap())
}
else {
result.notImplemented()
}
}
override fun onDetachedFromEngine(@NonNull binding: FlutterPlugin.FlutterPluginBinding) {
channel.setMethodCallHandler(null)
}
}
两个辅助类
package com.example.flutter_plugin0713;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
public class ConstraintsMap {
private final Map<String, Object> mMap;
public ConstraintsMap(){
mMap = new HashMap<String,Object>();
}
public ConstraintsMap(Map<String, Object> map){
this.mMap = map;
}
public Map<String, Object> toMap() {
return mMap;
}
public boolean hasKey(String name){
return this.mMap.containsKey(name);
}
public boolean isNull(String name){
return mMap.get(name) == null;
}
public boolean getBoolean(String name){
return (boolean) mMap.get(name);
}
public double getDouble(String name){
return (double) mMap.get(name);
}
public int getInt(String name) {
if(getType(name) == ObjectType.String) {
return Integer.parseInt(((String)mMap.get(name)));
}
return (int) mMap.get(name);
}
public String getString(String name){
return (String) mMap.get(name);
}
public ConstraintsMap getMap(String name){
return new ConstraintsMap((Map<String, Object>)mMap.get(name));
}
public ObjectType getType(String name) {
Object value = mMap.get(name);
if (value == null) {
return ObjectType.Null;
} else if (value instanceof Number) {
return ObjectType.Number;
} else if (value instanceof String) {
return ObjectType.String;
} else if (value instanceof Boolean) {
return ObjectType.Boolean;
} else if (value instanceof Map) {
return ObjectType.Map;
} else if (value instanceof ArrayList) {
return ObjectType.Array;
} else {
throw new IllegalArgumentException("Invalid value " + value.toString() + " for key " + name +
"contained in ConstraintsMap");
}
}
public void putBoolean(String key, boolean value) {
mMap.put(key, value);
}
public void putDouble(String key, double value) {
mMap.put(key, value);
}
public void putInt(String key, int value) {
mMap.put(key, value);
}
public void putString(String key, String value) {
mMap.put(key, value);
}
public void putNull(String key) {
mMap.put(key, null);
}
public void putMap(String key, Map<String, Object> value) {
mMap.put(key, value);
}
public void merge(Map<String, Object> value) {
mMap.putAll(value);
}
public void putArray(String key, ArrayList<Object> value) {
mMap.put(key, value);
}
}
package com.example.flutter_plugin0713;
public enum ObjectType {
Null,
Boolean,
Number,
String,
Map,
Array,
}
运行结果