(translated from French : Flutter, API natives et plugins (3/3))

It was also around May that the Flutter plugin system, a magnificent mechanism to easily use native features from Flutter/Dart, appeared.

In the first part we’ve seen the basics of MethodChannels In the second part we saw how to create a speech recognition dedicated channel

We’ll now see how to modularize this code by building a dedicated Flutter plugin for iOS and Android.

The Flutter plugin system 😍

Flutter plugins are managed as simple packages (dependencies), via pub the Dart package manager.

Just 1) declare the dependency, 2) run pub packages get , and Flutter will update the XCode and Android project. It is so effective and transparent, that for the moment I have not even had to understand what Graddle is, nor how a podfile works. Everything is managed by Flutter 😎🍹!

Even though the Flutter plugin catalog is still a little bit embryonic, It already offers some useful, if not necessary, tools.

Use a plugin

To use a plugin:

declare dependency in the pubspec.yaml of the project

dependencies:

speech_recognition: "^0.2.0+1" get the package, and build the app

flutter packages get

flutter build ios

flutter build apk Import the package in your code

import 'package:speech_recognition/speech_recognition.dart'; That’s all

… unless the plugin does require special permissions, in which case it is necessary to edit the .plist file for iOS, and manifest.xml for Android.

Then when the application is build, depending on the OS, Flutter will install and manage the iOS / Android dependencies, so that the native code is properly made available.

The team has set up a self-recording plugin system that works wonderfully, and in most cases, you have even not to touch iOS or Android files. 🍾🥂

Build a plugin

But the magnificence goes even further with the tooling to create plugins ! I found it so effective that I already published 4 plugins, while the least I can say, is that I was not at all a crossplatform plugin expert :).

The Flutter CLI provides a plugin scaffold generation command, containing all the necessary files, and even a pre-configured sample project using the created plugin :

flutter create -i swift --org bz.rxla --plugin my_plugin

-i swift : we want to use Swift for the iOS code, and not ObjC defined by default

: we want to use Swift for the iOS code, and not ObjC defined by default -a kotlin : if we want to use Kotlin instead of the Java default Android side

: if we want to use Kotlin instead of the Java default Android side --org my.domain : plugin namespace

: plugin namespace --plugin my_plugin : the name of the plugin

On the Dart side, the generated code is very simple, it mainly contains the creation of a “dedicated” channel. The most interesting aspect of this system is the self-detection / installation of plugins on iOS and Android.

Flutter / Dart

Here is the code generated for the Dart part of a plugin:

iOS / Swift

The SwiftPluginDemoPlugin.swift file contains the mechanism that allows an application to auto-detect the plugin. It’s a static register method, called by the application at launch to transmit a FlutterPluginRegistrar . The registrar role is to add the channel created by the plugin to the list of "receivers" of MethodChannel calls, to enable it to receive calls via its handle method.

The use of Swift adds a small layer, with the generation of both ObjC PluginDemoPlugin.h and .m files, and a SwiftPluginDemoPlugin.swift.

Android / Java

We find the same principle of registrar in Java for Android.

Implementation

From there, all that remains is to “move” the implementation from the second part to the plugin project, as well as the associated Swift and Java code. cf. Speech_recognition plugin

Publish

To publish a plugin on pub.dartlang.com :

/FLUTTER_PATH/bin/cache/dart-sdk/bin/pub publish

Resources