What is Flutter?
Flutter is Google’s UI toolkit for building natively compiled applications for mobile, web, desktop, and embedded devices with a single codebase. It was released on 4th Dec 2018 and has been growing since then. Today it has over 2 million users, and that number still keeps getting bigger.
To build apps with Flutter, you need to know the Dart programming language. Dart is an object-oriented programming language that aims to be as fast as possible on all platforms that use AOT (ahead-of-time) compilation with native machine code. In this article, we will go through the basics of Flutter. You will find out are the advantages of using it and how it is different from similar solutions, like React Native.
Flutter uses the declarative approach to build the views. This means that you describe the effect you want to achieve. For instance, if you want to display a list with Text, ProgressIndicator,andButton, you wrap these widgets in the Columnwidget. No need to write any additional code that would handle the rendering of UI elements.
This results in:
It’s a good moment to establish what exactly widgets are. They are fundamental building blocks in the Flutter world. Widget is a part of the User Interface. It could be either visible, like buttons or form fields, or invisible and serving to define the layout structure, such as column , row , or container. It’s all about nesting widgets inside other widgets and building more complex UI parts.
Type of Widgets
There are two types of Widgets – stateless and stateful . A stateless widget is a widget that does not have its state – which means that it is immutable. It cannot be changed during the app runtime. A stateful widget, on the other hand, can hold a state and is dependent on it. Every time the state changes, the widget is rebuilt with the new state value.
Make it faster with Flutter
One of the biggest advantages of Flutter is that you get plenty of out-of-the-box components. That means you don’t have to bother with tons of boilerplate code to make something look cool. If you want to implement some fancy, animated stuff like a collapsible app bar, you might just discover that there is a widget that lets you do that with a few lines of code.
Another feature that can speed up the development process is a hot reload feature. It works by injecting the updated source code straight into a running Dart Virtual Machine. In other words, the changes that you make are applied while the app is running. No more rebuilding the whole project just to see an updated text or color!
One codebase, multiple platforms
As we mentioned before, Flutter is about writing one codebase that can be delivered to different platforms. Currently, it supports mobile (Android and iOS), web, desktop, and embedded devices. This means you can build the app on the platform of your choosing.
Nobody likes reinventing the wheel. If you are working on a particular solution and you feel that you have seen something similar before, you should go to https://pub.dev/ to see if there is a package for that. There you can find solutions for various problems that have been previously experienced by other programmers. Need to work with the SqlLite database? Just grab sqllite package, import it to your project and start using it. It is that simple.
Mixing Flutter with native solutions
Imagine a situation when you need to create a custom element. There is no widget or package for that (highly unlikely!), and you need to trigger some native code to achieve it. Is it possible to run native Android or iOS code from the Flutter app level? Short answer, yes!
It is not an everyday treat to run a native code, because there is usually good Flutter-level support out there. But if for some reason you have to do that, you absolutely can!
Running native code
Flutter uses a message-passing style method to communicate with the native API. You need to create a MethodChannel object on the client (Flutter app) side. Then you can set a handler for messages from this channel on the host side (Native app). This channel allows clients and hosts to communicate with each other.
Let’s take a look at a real-life example. We will call an Android MainActivity method from the Dart code and get a result. First of all, we need to make a MethodChanel on the Flutter side. Make sure it has a unique name.
Next, we create a method in MainActivity class and set a handler for our MethodChannel:
When all this is done, we can call our native method from the Flutter app:
The above example shows how to do that for Android, but the method is similar for iOS.
Displaying native view
Sometimes you may want to use a native view in your Flutter app – for example, Google Maps from Android and iOS. There is a Platform Views feature that allows you to do just that. By using it, you can write native views that need to touch a native code, and then just put it straight into your widget tree.
Currently, Flutter can render Android native views by using Hybrid Composition or Virtual Display.
With Hybrid Composition , a native android.view.View will be added to the view hierarchy, which means full support for accessibility or keyboard handling.
On the other hand, with Virtual Display, the native view will be rendered simply as a Texture and it will not be a part of the view hierarchy. It might cause some issues with interactions such as handling a keyboard.
When it comes to performance, there are a few trade-offs. Generally speaking, Virtual Display is more efficient but also more limited than Hybrid Composition.
iOS uses only Hybrid Composition, so the native UIView is appended to view hierarchy.
How Flutter is different from similar solutions like React Native
React Native and Flutter have a common goal – to let you deliver an app to multiple platforms by using a single codebase – but the difference lies in how they try to reach it. Here are a few basics differences:
With Flutter, the application is compiled ahead of time into a native code, which results in better performance.
The way the app is rendered on the mobile device screen is the biggest difference between Flutter and React Native.
The Flutter way of drawing your app is radically different. Instead of using native components, Flutter draws them on a screen canvas from scratch, using a very efficient 2D graphics library – Skia. It owns and controls every pixel on the screen. That is why it is usually more efficient than the competition.
The result can be either positive or negative, depending on the point of view. Because Flutter does not rely on native components and draws everything by itself, your app will look the same on every platform and every OS version! Your Flutter app should look and behave the same on Android 5 and 12. It also means that every component will work identically everywhere. With RN, on the other hand, the situation that components have some attributes that are working only on Android or iOS is quite common.
On the screenshots below you can see the same Flutter app running on Android 11 and Android 4.1:
As you can see, the app is using Material Design, which was created in 2014. Android 4.1 was released 2 years earlier, in 2012– so it does not have any native support for Material Design components. Flutter can still handle that because it renders every pixel by itself.
As React Native is a kind of wrapper over native UI elements, it provides only basics components. With Flutter, you have access to a rich widgets catalogue. Those are not just simple elements (like buttons) but even more powerful structures, like animated app bars, bottom bars, expandable views, and much more. If you want to learn more, see the widget catalog.
Flutter has become quite popular over the years. It allows you to create for various platforms by using the same codebase and keep a native performance. A lot of built-in widgets are waiting to help you create beautiful apps.
All these things make Flutter a framework that you cannot simply ignore.
If you want to learn more, look at the official Flutter website.