在Flutter中,想要调用原生的api,需要通过MethodChannel的方式(常用的方式,其他的方式暂不介绍),下面介绍的方式,是在vscode中的方法。
1 生成Package在vscode的工作台中,通过命令行创建一个package plugin
flutter create --org com.example --template=plugin --platforms=android,ios -a java hello
这样是创建了一个支持ios和Android 名称为hello的插件,其中包含了Android的工程和ios的工程,以及flutter的入口hello.dart.
2 MethodChannelMethodChannel是Flutter和原生交互的基础,通过传入Flutter插件的名字,调用invokeMethod方法,便可以调用原生的方法,有点类似于Java的反射。
static const MethodChannel _channel = MethodChannel('hello');
static Future<String?> get platformVersion async {
//调用原生代码
final String? version = await _channel.invokeMethod('getPlatformVersion');
return version;
}
在Android端,通过一个处理类,继承自MethodCallHandler需要接受Flutter调用方法的请求,返回原生数据。
public class HelloPlugin implements 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 MethodChannel channel;
@Override
public void onAttachedToEngine(@NonNull FlutterPluginBinding flutterPluginBinding) {
channel = new MethodChannel(flutterPluginBinding.getBinaryMessenger(), "hello");
channel.setMethodCallHandler(this);
}
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull Result result) {
//如果Flutter端调用了getPlatformVersion方法,那么就返回数据;
//返回数据通过MethodCall的success方法
if (call.method.equals("getPlatformVersion")) {
result.success("Android " + android.os.Build.VERSION.RELEASE);
} else {
result.notImplemented();
}
}
@Override
public void onDetachedFromEngine(@NonNull FlutterPluginBinding binding) {
channel.setMethodCallHandler(null);
}
}
3 第三方SDK配置
在Android目录下的build.gradle中,像在Android工程中配置一致,最好在Android Studio中打开,编写Android端的代码
4 Package包发布pub和本地依赖当插件完成之后,可以将package包发布到pub上,flutter调用原生代码,就可以依赖这个插件,调用其中的方法。
其实,package发布的时候,坑还是挺多的,如果不想发布也能迅速使用插件,可以通过本地依赖的方式,导入插件;
dev_dependencies:
flutter_test:
sdk: flutter
# The "flutter_lints" package below contains a set of recommended lints to
# encourage good coding practices. The lint set provided by the package is
# activated in the `analysis_options.yaml` file located at the root of your
# package. See that file for information about deactivating specific lint
# rules and activating additional ones.
flutter_lints: ^1.0.0
//这就是插件
hello:
path: hello
在使用的时候,可能没有那么智能,需要自己手动导包。
import 'package:hello/hello.dart';
5 Flutter端调用Android端代码
static Future<String?> get setupCommonProperties async {
//调用原生代码
final String? result =
await _channel.invokeMethod('setupCommonProperties', {
'userId': 'user_001',
'gid': 'gid_001',
'city': '北京',
'grade': '三年级',
'grade_id': 'grade_001',
'city_id': 'city_001',
'args': {'sex': '男', 'age': 12}
});
print('$result');
return result;
}
Flutter端,通过MethodChannel的invokeMethod方法,调用Android端的方法如下:
//设置公共参数
if(call.method.equals("setupCommonProperties")){
//获取传入的请求参数
// String userId = call.argument("userId");
// call.argument
String userId = call.argument("userId");
Log.e("TAG","userId=="+userId);
String gid = call.argument("gid");
String city = call.argument("city");
String grade = call.argument("grade");
String gradeId = call.argument("gradeId");
String cityId = call.argument("cityId");
Map<String,Object> args = call.argument("args");
// //调用原生api
DataManager.getInstance().setupCommonProperties(userId,gid,city,grade,gradeId,cityId,args);
// //返回结果
result.success("设置公共参数完成");
}
如果想要获取Flutter端传入的参数,通过MethodCall的argument取出参数,调用原生的api,通过Result向Flutter端返回结果。
6 小结Flutter端调用原生代码,在混合开发中是非常常用的。Flutter的性能毕竟不如原生的性能好,有些模块可能必须要依赖原生的能力,这时候,MethodChannel作为Flutter和原生的桥梁,就起到了很大的作用。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)