Platform Channel And Reversed Platform Channel With Flutter

Destiny Ed
7 min readApr 13, 2022

--

There are so many plugins available for using platform specific API in your flutter application. What if you want to create a new plugin or you want to implement some functionality in your app that don’t have a plugin yet?

Well, We will be looking at the possible way to write and use platform specific API in your flutter application. But first, We will be looking at platform channel showing a Native Toast message in our flutter application. After that, We will look at the Reversed Platform Channel. Don’t get scared yet about this topic because it will be broken down completely for better understanding.

Note : This article only focus on writing platform-specific code for Android using Kotlin(You can also use Java) but same logic can be applied to IOS if you know your way around IOS development.

Platform Channel

Platform channel is a way to connect flutter app with Native API.

Flutter platform channel uses a flexible language system that works with platform(Native) API. What I mean is this, platform channel works with any type of language as long as the target platform supports that language.

Let’s say for example, you want to use some API for Android, you will be using languages like Java or Kotlin. For IOS or MacOs, you will use Swift or Objective-C. For Windows and Linux, you will use C++ and C respectively.

How does platform channel work?

I guess that’s the question racing through your mind now, yeah?

Platform channel works asynchronously within your flutter application. You can imagine it as an HTTP call to the server but in this case every thing happens within your flutter application without any external call.

Let me break it down using bullets

  • The flutter portion of your application makes an asynchronous call to it’s Host(Native portion). Basically, Flutter portion sends a message to the Native portion of your application using platform channel.
  • The Native Portion(Host) receives the call or message and then it calls any method or API matching the message sent from the flutter portion.
  • After performing the action, It sends a response back to the client(flutter portion) which then displays and show the response to the user.

If you notice, it works like a client-server service over the internet.

Some Important things to know before using platform channel

  • Method Channel : This channel enables us to send messages or invoke a method that corresponds to the one declared in the native side of your application.
  • Invoke Method : This is a method from the Method channel class for invoking native methods.

Note : Method Channels and Methods calls can be called in a reversed direction(Reversed Platform Channel). This way the Native platform of your application acts as a client. We will treat that later…

Limitations:

The only limitation I know for know is that you will have to write Native code with different languages depending on the platform you are targeting.

Also, Since platform channel is asynchronous, It takes some time to call and return a response depending on the Native API you are trying to use. Sometimes, this will cause some delay in your flutter app User Interface or cause Jank(UI hanging).

However, you can try as much as possible to limit the number of async functions you are calling on the UI thread to avoid most of the limitations above.

Platform Channel Implementation

“For the things we have to learn before we can do them, we learn by doing them.”
Aristotle

From this part until we start looking at reversed platform channel I will be showing you the most easy way of implementing platform channel.

The following code snippets will demonstrate how to write platform specific API to show a Native(Android) Toast message.

Create a new flutter project

I would recommend you use Android studio to implement this as you will be able to spot error easily. But if you are okay with VsCode or any other IDE then no worries.

I believe we all know know how to create a new flutter project using android studio or terminal. If you are like me and you prefer using the terminal, then run the following command

“flutter create toast_app”

Create method channel

In your app “main.dart” file create a static Method channel variable with a unique “name” as parameter. In our case, we will be using “destinyed” as the channel name.

import 'dart:async';import 'package:flutter/material.dart';import 'package:flutter/services.dart';class _MyHomePageState extends State<MyHomePage> {static const platform = MethodChannel('destinyed');// Show Toast.

Note : This channel name will be used in the Native portion of your app for identification and communication because you don’t want the platform channel to be confused.

Create a showToast method

Create a simple dart method that will handle the communication to the native portion of your application.

Future<void> _showToast() async { try {   final result = await platform.invokeMethod('showToast');   print(‘result); } on PlatformException catch (e) {   print(e.toString()); }}

Remember I told you before now that platform channel works asynchronously.

Looking at the above method you will notice that I used async…await keyword to call the native API using the ‘invokeMethod” from the “MethodChannel” and then I passed the name of the function/method I want to call in the Native portion(We will create the method shortly).

Also, I wrap the whole code in a try…catch block for handling errors that might arise while making the call. I did that because the Native API might fail in returning the result we want and sometimes we are not in the best position to know the cause of the exception or what is happening under the hood.

Trigger the flutter method to call the Native API

Now that will have the method to communicate with the Native API we need to trigger the method.

So for this, We will be creating a floating action button(You can use any button) that will trigger the method and then return the response we need.

@overrideWidget build(BuildContext context) {  return Scaffold(    appBar: AppBar(      title: Text("Platform channel"),    ),    floatingActionButton: FloatingActionButton.extended(       onPressed: _showToast,       label: Text("Show Toast"),    ), );}

Alright, Now that will are done with the flutter implementation, lets look at the Native implementation for Android.

Follow the steps below to launch the Android module of your Flutter app in Android Studio:

  • Start Android Studio
  • Select the menu item File > Open…
  • Navigate to the directory holding your Flutter app, and select the android folder inside it. Click OK.
  • Open the file MainActivity.kt located in the kotlin folder in the Project view.

Your MainActivity.kt file should look like this after you open it… Don’t get scared as nothing serious is happening here lol.

import androidx.annotation.NonNullimport io.flutter.embedding.android.FlutterActivityimport io.flutter.embedding.engine.FlutterEngineclass MainActivity: FlutterActivity() {      override fun configureFlutterEngine(@NonNull flutterEngine:                   FlutterEngine) {       super.configureFlutterEngine(flutterEngine)    } }

Register a Method Channel with your unique channel “name”

Remember we created a channel and we used ‘destinyed’ as the name. So, In this case we are also going to use the same name to avoid conflict in channel communication.

import androidx.annotation.NonNullimport io.flutter.embedding.android.FlutterActivityimport io.flutter.embedding.engine.FlutterEngineimport io.flutter.plugin.common.MethodChannelclass MainActivity: FlutterActivity() {private val CHANNEL = "destinyed"override fun configureFlutterEngine(@NonNull flutterEngine: FlutterEngine) {super.configureFlutterEngine(flutterEngine)MethodChannel(flutterEngine.dartExecutor.binaryMessenger, CHANNEL).setMethodCallHandler {call, result ->// Note: this method is invoked on the main thread.// TODO}}}

From the above snippet, We have a MethodChannel that takes two(2) parameters : BinaryMessenger and Channel. This methodChannel also has a MethodCallHandler that we can use to listen to the call coming from flutter portion and also a ‘result’ which we can use to return a response back to flutter portion of our application.

Finally, handle the call

Now that we have the Method channel and call handler ready, we can use the ‘call’ to check for the corresponding method that the flutter portion is willing to call and ‘result’ to send a response back to the flutter portion after utilizing the API

if (call.method == "showToast") {//Show ToastToast.makeText(this, “Hello Flutter”, Toast.LENGTH_LONG).show()result.success(“Toast started”)}else {result.unImplemented}

Now, the above snippet actually shows a Toast message if the ‘call.method’ is same as the method we tried to call from the flutter portion with a ‘Toast started” response using the ‘result.success’ callback.

There are three callback we can return using the ‘result’

  • result.success(“Success message”)
  • result.error(“Error message”)
  • result.unImplemented (This is called when the method we want to call from the flutter portion does not match any method from the Native portion.

There you have it guys

In summary, Platform Channel represents a way to call native code in other to use native functionality within a Flutter application. It can be used to create flutter plugins targeting any platform of your choice.

With platform channel, You are certain to build any type of application with flutter that can also be built with Native Sdk. So no worries, Flutter has no limitation when it comes to Mobile application development.

Platform channel is well documented in the official documentation in case you wish to check it out.

Reversed Platform Channel

As the name reads, reversed platform channel represents the way of calling flutter methods or packages from the Native portion of your application.

In this case, Flutter portion of your app works as the Host while the Native portion works as the client that is requesting the data.

More on Reversed Platform Channel will be coming soon…

Thanks for reading… I will write to you again in the future.

--

--