前言

虽然现在已经有很多插件了,但是有时候还是需要自己开发一个插件。因此打算学习一下如何开发一个插件。这里只考虑安卓,安卓使用kotlinkotlin不会也没事,我也不会。

参考项目:https://github.com/TBoyLi/flutter_plugin_learning

参考教程:https://www.jianshu.com/p/9fc6747fc7c4

创建插件项目

1、文件、新建、新建flutter项目

flutter写ios插件如何引入第三方库 flutter插件开发教程_ide


2、选择flutter、下一步

flutter写ios插件如何引入第三方库 flutter插件开发教程_ide_02


3、维护好基础信息,项目类型选择插件

flutter写ios插件如何引入第三方库 flutter插件开发教程_flutter_03

开发

项目目录如下,后续需要编写的文件是

  • BatterylevelPlugin.kt 编写原生代码
  • batterylevel.dart 编写dart代码,flutter项目中会使用该文件
  • batterylevel_method_channel.dart 用于编写与原生通信的逻辑
  • batterylevel_platform_interface.dart 定义了需要实现哪些方法

batterylevel_platform_interface.dart定义了一个获取平台接口的方法。

batterylevel_method_channel.dart中重新了该方法,并与原生通信

BatterylevelPlugin.kt 实现了原生逻辑

flutter写ios插件如何引入第三方库 flutter插件开发教程_flutter_04

安装上面的方式,我们定义一个获取当前电量的方法。
batterylevel_platform_interface.dart

// 获取电池电量
 Future<int?> getBatteryLevel() {
   throw UnimplementedError('getBatteryLevel() has not been implemented.');
 }

batterylevel_method_channel.dart

/// 获取电池电量
@override
Future<int?> getBatteryLevel() async {
  final level = await methodChannel.invokeMethod<int>('getBatteryLevel');
  return level;
}

BatterylevelPlugin.kt

编写原生代码时,创建一个新的窗口打开安卓部分,这样会有提示,也不会出现报错。

选中项目,鼠标右键

flutter写ios插件如何引入第三方库 flutter插件开发教程_ide_05

打开后,两边对照一下,别打开错了。

flutter写ios插件如何引入第三方库 flutter插件开发教程_flutter_06

/** BatterylevelPlugin */
class BatterylevelPlugin: FlutterPlugin, MethodCallHandler {

  private lateinit var channel : MethodChannel
  // 获取上下文对象
  private var applicationContext: Context? = null


  // 注册插件到flutter引擎
  override fun onAttachedToEngine(flutterPluginBinding: FlutterPlugin.FlutterPluginBinding) {
    // 上下文对象
    applicationContext = flutterPluginBinding.applicationContext
    // 创建通道
    channel = MethodChannel(flutterPluginBinding.binaryMessenger, "batterylevel")
    channel.setMethodCallHandler(this)
  }

  override fun onMethodCall(call: MethodCall, result: Result) {
    // 判断通信方法的名称,实现获取平台版本
    if (call.method == "getPlatformVersion") {
      result.success("Android ${android.os.Build.VERSION.RELEASE}")
    } else if(call.method=="getBatteryLevel"){
       // 返回电量
      val batteryLevel = getBatteryLevel()
      if (batteryLevel != -1) {
        result.success(batteryLevel)
      } else {
        result.error("UNAVAILABLE", "Battery level not available.", null)
      }
    }
    else {
      result.notImplemented()
    }
  }
  // 获取电池电量
  private fun getBatteryLevel(): Int {
    var batteryLevel = -1
    batteryLevel = if (VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
      val batteryManager = applicationContext?.let { getSystemService(it, BatteryManager::class.java) }
      batteryManager!!.getIntProperty(BatteryManager.BATTERY_PROPERTY_CAPACITY)
    } else {
      val intent = ContextWrapper(applicationContext).registerReceiver(null, IntentFilter(Intent.ACTION_BATTERY_CHANGED))
      (intent?.getIntExtra(BatteryManager.EXTRA_LEVEL, -1) ?: -1) * 100 / (intent?.getIntExtra(BatteryManager.EXTRA_SCALE, -1)
        ?: -1)
    }

    return batteryLevel
  }

  override fun onDetachedFromEngine(binding: FlutterPlugin.FlutterPluginBinding) {
    channel.setMethodCallHandler(null)
  }

}

batterylevel.dart

// 获取电池电量
Future<int?> getBatteryLevel() {
  return BatterylevelPlatform.instance.getBatteryLevel();
}

测试

在插件的example里测试

example下的main.dart

flutter写ios插件如何引入第三方库 flutter插件开发教程_flutter_07

class _MyAppState extends State<MyApp> {
  String _platformVersion = 'Unknown';
  final _batterylevelPlugin = Batterylevel();

  // 电量
  String batteryLevel = '';

  @override
  void initState() {
    super.initState();
    initPlatformState();
  }

  ///获取版本号
  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 _batterylevelPlugin.getPlatformVersion() ??
          'Unknown platform version';
    } on PlatformException {
      platformVersion = 'Failed to get platform version.';
    }

    if (!mounted) return;

    setState(() {
      _platformVersion = platformVersion;
    });
  }

  // 获取电量
  Future<void> getBatteryLevel() async {
    try {
      int res = await _batterylevelPlugin.getBatteryLevel() ?? 0;
      batteryLevel = res.toString();
    } on PlatformException {
      batteryLevel = 'Failed to get battery level.';
    }
    // 更新
    setState(() {});
  }

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: const Text('Plugin example app'),
        ),
        body: Center(
          child: Column(
            children: [
              Text('Running on: $_platformVersion\n'),
              Text('电量:$batteryLevel\n'),
              ElevatedButton(onPressed: (){
                getBatteryLevel();
              }, child: const Text("获取电量"))
            ],
          ),
        ),
      ),
    );
  }
}

flutter写ios插件如何引入第三方库 flutter插件开发教程_Text_08

在flutter项目里加载本地的这个插件

最开始是打算直接在项目里引入插件的,奈何引入后一直提示路径不对。因此改成通过git引入

1、将你的插件提交到git仓库

2、在flutter项目的pubspec.yaml引入插件

flutter写ios插件如何引入第三方库 flutter插件开发教程_flutter_09


3、运行 flutter pub get 获取依赖下载的依赖一般都在用户目录下,如下图

flutter写ios插件如何引入第三方库 flutter插件开发教程_flutter_10


flutter写ios插件如何引入第三方库 flutter插件开发教程_Text_11


4、就跟其他依赖一样,正常使用即可

class _MyHomePageState extends State<MyHomePage> {
  // 获取电池电量的本地插件
  final Batterylevel batteryLevel = Batterylevel();
  // 当前电量
  int batteryLevelValue = 0;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        backgroundColor: Theme.of(context).colorScheme.inversePrimary,
        title: Text(widget.title),
      ),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: <Widget>[
            Text("当前电量是:$batteryLevelValue"),
            ElevatedButton(
                child: const Text("获取电量"),
                onPressed: () async {
                  int res = await batteryLevel.getBatteryLevel() ?? 0;
                  setState(() {
                    batteryLevelValue = res;
                  });
                })
          ],
        ),
      ),
    );
  }
}

flutter写ios插件如何引入第三方库 flutter插件开发教程_flutter_12