EntrenaPro — From Zero To Flutter

Published 40+ Screens App in 4 Months built with Flutter + ❤️

Purpose of this post is to share my journey and inspire other tech companies to choose Flutter for their next project.

The Beginning

It begins when Peri, the Product Owner who had worked with me before asked if there was any possibility if re-doing all the mockups for EntrenaPro iOS and Android app in less than 4 months. He shared invision link for the project. He was open to choose any cross-platform framework that can help us to deliver in a very tight deadline. EntrenaPro is an app where Coaches and Athletes can schedule individual and public sports sessions between more than 40 activities all over Spain.

My Introduction With Flutter

In 2015 I saw above video that time I liked the idea but I never got the opportunity to try it. Until project came in with a very tight deadline and an app was needed to build for both platforms. And I was free to pick any framework, so I chose Flutter. Since 2015 Flutter has come a long way.


Why I Choose Flutter, Not React Native

“photo of fighting bison” by Richard Lee on Unsplash

When I had to decide at that time I had no experience with Flutter and one week of experience with React-Native (I started an app on my own that I never finished). These were the points in decision making:

  1. Speed of delivery, Developer productivity. I had read about it on multiple places
  2. When Flutter paints the screen it uses its own surface and draws Widgets (Views, Buttons, Texts) on that surface, so Flutter has control of each and every pixel on the screen. Flutter doesn’t use OEM widgets. On the other hand, React Native uses OEM widgets to draw Components on the screen. It means when you draw a widget using Flutter, it will look 100% the same on each platform, no matter if the platform OEM widget has support for it or not. And Flutter also has platform aware widgets and platform aware physics
  3. Flutter uses Dart language which has datatypes (previously optional but from version 2.0 Strong Datatypes), I am coming from Java/Swift so for me Dart is cooler than Javascript, I have read articles people using TypeScript (I love this language too) or Flow but It’s better than data types are built into the language, it helps IDEs to understand the code and enable IDE to suggest code completion.
  4. I am biased towards Google products

I don’t want to give an impression that RN is bad, no doubt many successful apps have been developed in RN and they look GREAT. But my first 6 days encounter was not pleasant (try to create a view with shadow properties x = 0, y = 2, blur = 6, spread = 0 and test it on both platforms), so I tried something new. Flutter and React Native offers Cross-Platform development differently and I personally like the Flutter approach more.


My Journey With Flutter

“gray concrete road” by Zachary Varga on Unsplash

Installation

The installation process was easy for me. I assume as Android developer you already have the Android Studio in your system
1. Clone the Flutter repo
2. Setup environment variables
3. Run `flutter doctor` command
4. Install flutter plugin in Android Studio
That’s It.
Here is the more detailed official guide https://flutter.io/get-started/install/
I never faced the trouble during the installation but I have seen other people facing issue during installation process and Flutter community is very helpful in this regard.

Picking Up Dart and Flutter

I was coming from Java and I started to write basic Dart on the first day, the syntax was very similar and in later days my grammar started to improve and it is still improving. Dart has built-in support for Streams and Futures. My RxJava knowledge helped me with streams and ES6 Promise knowledge helped me with Futures, Async/Await. I was productive from day one. I feel people coming from Strongly Typed languages will pick it up early but people coming from dynamic languages will face little hard time.

In Flutter everything is Widget. This was a different thing for me, but documentation and tutorials helped me a lot in getting started. My first two-three days were very confused because there were a lot of new concepts, lay outing, styling, padding everything was a Widget. And after mapping concept from Android UI system to Flutter UI system things started to get easier. I started to feel more confident. And I very much like the Declarative way of UI.

Above all Flutter Hot Reload and Hot Restart features were reducing the testing time, every UI change takes only 0.7 (mostly) ~2 (sometimes) seconds at max to appear on the screen in my project. Plus Flutter also maintains the state of the Widget. If you have entered the text and selected the checkboxes and now you are changing the checkbox color it will change the color only and will keep them selected. It helps me to show more productivity. If I calculate then I think it could save more than 40% of the time w.r.t. testing in native development.

Like any other good programming language Dart also have package management solution. https://pub.dartlang.org/ They call it Pub. Dart officially supports it. It is very similar to NPM.

First Week, First Screens, Adaptability, Reusability

In my first week, I completed Login and Registration screen and result was phenomenal. Adaptability was great, when I sent the device screenshots to the designer he said, “Wao, very balanced”

Login screen adaptability on different screen sizes

Flutter uses Declarative way of UI, it increases the widget reusability a lot, and I created a “Bonus” widget and used it on multiple places, same for “User Avatar”. Extracting anything into a widget is easy and the widget can be reused anywhere.

Challenges I Enjoy

In Flutter you not face the challenges but you enjoy them.
Athlete on boarding sequence on OPPO F7

For example, according to a design of a screen I need a month picker and there was no readily available package for that to use, PageView widget was closely resembling to the UI, I dig into the code I understand it and I created my own Widget and published it to the Pub.

And on another screen, I needed a range slider but there was only Slider available with a Single thumb, I dig into the Cupertino Slider code and created a new Range Slider Widget and published it to Pub.

Some random screens from the app on OPPO F7
Coach creating sport session sequence on OPPO F7

Stripe Integration

It was a challenge because there was no official support in Dart. There were few packages available in Pub but we needed more detailed integration. I decided to write Plugin (A specialized Dart package which contained an API written in Dart code combined with a platform-specific implementation for Android using Java or Kotlin, and/or for iOS using ObjC or Swift) for that. But when I checked official SDK of stripe for iOS and Android on github I found their code was not similar in terms of the function signature. In Android SDK theirs one function returns the result but counterpart iOS SDK returns nothing. So I skip this idea and moved to the next one, which was write a package by reading their documentation and I followed documentation and Android SDK as a reference and completed set of features required by the App.

Push Notifications

Left OPPO F7, Right IPHONE 7

I used Firebase Cloud Messing for both iOS and Android. Flutter had an official plugin for that, First I used that plugin to integrate Push notification. But later requirements changed and we had to make real-time updates on screen content based on the data in the notification. That was the point where I had to include platform channels in project. I removed the official plugin from the project and started to write my own Firebase integration code for android(Java) and iOS (Swift). Using platform channels I also started to push the data on Dart side whenever I received notification on the platform side. It also enabled me to open specific screen based on notification type when user taps on the notification.

Code Structure

On a large project structuring the code plays a very important role, when I started the project popular options were: 1. Redux, 2. Scoped Model. I started to follow Redux, I personally don’t like redux, putting everything in one store is not my taste, but luckily in Google IO 2018 they give a talk about this topic and I started to convert architecture to BLOC pattern. It is fulfilling every purpose and still I am learning the best practices in BLOC pattern

Translations

We were near the deadline and Product Owner thought we needed to add one more Developer so he can work on translations in parallel. I did a mistake (or I was a beginner) during the development I did not extract out the Strings in app localization file, so other developer took the responsibility and extracted out the string and completed the translations file, It took him one week to complete the translations

Later product owner asked me to change some of the translations in the app, to make it more meaningful and then I realized how hard to work with translations in Flutter as compared to Android. We used Dart intl tools for generating .arb file and then back .dart file.

Creating Builds and Publishing

Creating builds are easy, documentation helps a lot when you have to create a release build. If you feel comfortable while creating builds on Xcode and Android you will feel yourself at home. There are just a few extra commands that generate dart executable code, and then for Xcode we follow normal procedure Build/Archive/Upload to Store. For Android, after setting keystroke simple one command creates a release build.

App Store just took one day to approve and listed on their store and App is available to download on both stores.

What’s Next For Me

Nowadays I am focusing on Animations/Hero Animation and Custom widgets. I have to dig deeper into the in-code documentation and have to learn advance stuff. Isolates are next topic for me, where we have to perform some heavy lifting task on background threads. Schedule was very tight and we focused on finishing the app the soonest possible, so we didn’t focus on the test cases. Next thing is to be well versed with test cases in Flutter. In the end, I also have to learn Continuous Integration/Continuous Delivery.

Conclusion

I found Flutter is the best candidate for business apps. It helped me to complete the first version of the app in a very tight deadline. As a developer it gives me satisfaction that if UI is looking beautiful on iOS then it will look the same on Android. If you have to access something platform specific then there is a mechanism to do that, and it is easy. Dart language is easy to pick. Flutter HotReload saves a lot of time and increases productivity. Community is growing. Plus better tooling and IDE support.


About me: I’m an Android & Flutter developer, juggling between contract work, open source and side projects. That’s all, thanks! If you liked this post, don’t forget to leave a 👏!


App Features Overview

After reading a long post if you still interested what set of features an App built using Flutter could offer, here is the detail, EntreaPro App offers the following features set so far:

  • Two very different roles (Athletes and Coaches) with different options, payments, side menus, and features.
  • Geolocated searches for Coaches and Athletes(using Place Suggest API ).
  • General view for scheduled sports sessions categorised by pending, accepted and cancelled.
  • Stripe Connect integration (using webview to handle redirection response) to let every Athlete pay sessions to coach by Credit Card.
  • Stripe integration (using custom api built in Dart)to let Coach pays a subscription to EntrenaPro.
  • Sports bonus sold by Coaches where a number of tickets ready to be ticked after any session.
  • Real-time updates and notifications (using Firebase Push Notification) for new Session Requests, Acceptance, Cancellations, Payments…
  • Calendar picking to filter available time for any professional.
  • Rating system with 5-stars, comments and replies
  • Coach notebook to let him keep track of his offered sessions vs athlete performance
  • Coach profile sharing (using firebase dynamic links)