Andrew Baisden I’m a full-stack developer from London. Programming is one of my passions in life. A majority of my most recent skills have been self-taught. I find this is one of the best ways to learn because you can go at your own pace.

Flutter vs. React Native

10 min read 2873

Flutter Vs React Native

The two most popular cross-platform mobile app development frameworks available at the moment are Flutter and React Native. These juggernauts are backed by two of the largest tech companies in the world: Flutter was created by Google and React Native was created by Facebook.

In this guide, we’ll compare Flutter vs. React Native, explore what makes each framework so special, and discover why they’re so highly sought-after.

Here’s what we’ll cover:

To see how React Native stacks up against Xamarin, another popular cross-platform mobile framework, check out “Xamaris vs. React Native.”

What is Flutter?

Flutter is a cross-platform UI framework developed by Google. It was first released in May 2017 and has steadily grown in popularity over the years.

One of Flutter’s main selling points is that it enables you to create cross-platform applications using a single codebase. Traditionally, if a company wanted to create an application that was available on the web, mobile, and desktop, it would have to use more than one tool to achieve that goal. For example, it might need to hire a developer who specializes in web development, another developer who has experience building desktop apps, and a dedicated mobile developer to build apps for iOS and Android.

In a situation like this, you might have one developer using React to build the website, another using C# and Java to create the desktop version, and Kotlin and Swift to build the Android and iOS apps, respectively. This would require a whole team of developers, not to mention a ton of meetings to make sure the design and branding is consistent across all platforms. You also have to factor in testing for each platform and addressing their respective bugs and quirks.

With Flutter, companies can hire one developer to create apps across platforms with just one codebase to manage. This cuts down significantly on the time and resources required to launch and maintain an application.

Thanks to Flutter one developer can potentially create apps across all of these platforms with just one codebase to manage which would cut down on time and resources.

What is React Native?

React Native is a cross-platform framework created by Facebook. It makes it fairly simple to create cross-platform applications because the codebase is essentially written in JavaScript. This lowers the barrier to entry for JavaScript developers because they don’t need to learn a completely unfamiliar language.

We made a custom demo for .
No really. Click here to check it out.

Web development has been around for many years and most web developers have been using JavaScript for much of their career. Mobile development is still fairly new, but the ecosystem has matured quite a bit over the past few years. If you already know JavaScript, the learning curve for mobile app development using React Native won’t be as steep.

These days, many companies are using React Native for app development. Microsoft recently developed its new Xbox store app using React Native, for one prominent example. Like Flutter, React Native makes it possible to create apps across various platforms using one codebase.

Key differences between Flutter and React Native

Flutter and React Native share a lot of similarities, but they are also quite different in a handful of key ways.

For starters Flutter uses the Dart programming language in its codebase whereas React Native uses JSX, which stands for JavaScript XML. Both languages are based on the C-style type of syntax and follow object-orientated principles. This common ground it means that Flutter and React Native are fundamentally alike in terms of design and the code is very similar as well.

Dynamic vs. static programming

There is a significant difference when it comes to the core programming language. JavaScript is dynamic by nature. This means you can change the values of various data types, which makes it very versatile. Dart is both dynamic and static, which allows it to have the best of both worlds.

A statically typed language is generally considered much safer since it forces you to declare and use the correct data type. For example, you can’t assign a number to a string; doing so would throw an error.

Static means you’re likely to experience fewer errors. It is possible to enforce more type safety and error checking with JavaScript if you opt to use TypeScript, which is a strict syntactical superset of JavaScript, instead.

Layout

Flutter uses a widget style for constructing the user interface whereas React Native uses JavaScript and JSX. Flutter widgets are premade, so you don’t technically need to create your own custom widgets unless you want to. Since they were created and tested by Google, you don’t need to worry about incompatibility issues.

One thing I should mention is that if you’re using a programming language such as Swift for mobile app development, you typically can’t see the code that Apple used to create user interface components, such as buttons. With Flutter, by contrast, the code is viewable so you can see how Google created all the widgets.

Flutter and React Native share common ground when it comes to constructing the layout in that they both use CSS Flexbox. The way they implement it is different, but as long as you know Flexbox, you shouldn’t have any problems building the layout for your app. The team that worked on Flutter also worked on the developer tools for the Google Chrome browser, which makes for a quick transition since the debug tools are quite similar.

Why is mobile app development so popular?

The field of mobile app development has grown steadily over the past few years. Almost everyone on the planet has a mobile phone, so the user base is massive. These days, you can find an app for almost anything.

There are quite a few paths you can take if you want to create a mobile app. You could choose to go down the native route, which would mean using Swift to create mobile apps or Kotlin to create Android apps. These are the official programming languages Apple and Google use, respectively, so you can expect first-party support and frequent updates.

Alternatively, you could choose to go down the cross-platform path and use Flutter or React Native. Typically, a native developer would use Xcode and Swift to build iOS apps and Android Studio and Kotlin for Android apps. These tools are applicable for cross-platform work. It’s also quite common for developers to use an integrated development environment (IDE) such as Visual Studio Code.

In most cases, developers tend to use an IDE, Android Studio, or Xcode when building apps with Flutter and React Native. My preference is to use Visual Studio Code for React Native apps and Android Studio for Flutter apps. Android Studio actually has a Flutter plugin with code helpers, which makes it much easier to write and debug your code. As of right now, this plugin has 8.3 million downloads, which goes to show just how popular it is.

At the time of writing, React Native is slightly more popular than Flutter, thanks in part to React Native’s association with the popular web framework React. React Native has also been around for longer so its user base is larger. As such, there is currently higher demand for React Native developers than for Flutter developers.

Flutter vs. React Native: Performance

Both Flutter and React are open-source, which means they’re free to use. Both libraries are well-maintained, as you would expect considering they’re created by Google and Facebook. It is possible to test apps created using both frameworks, either virtually using a built-in simulator on your computer for iOS and Android or natively on your phone. You’ll need an Apple computer if you intend to develop on iOS since the SDK is only available on Apple computers. Windows users and Linux users are out of luck. Fortunately, you can develop Android development apps on any platform.

Both frameworks use hot reloading so you can make changes and see them instantly. This makes development more efficient because you don’t have to keep stopping and starting your apps to see updates.

There is some debate as to whether Flutter and React Native are truly native. The be considered 100 percent native, they would need to be written in the language they were designed for — namely, Swift for iOS and Kotlin/Java for Android.

The experience you get when using an app that was written in React Native and Flutter is, for the most part, a native experience. The Dart code, which Flutter uses, is complied to C, which is about as close to native as you can expect. You can safely assume that would make for better performance.

The company that created Reflectly recently moved the app from React Native to Flutter and saw a significant increase in performance. This is one example of an improvement. However, it won’t be the same for every app; there are many edge cases to consider, such as the type of app, codebase, database, phone, operating system, etc.

Flutter vs. React Native: Developer ecosystem

Developers who are keen on building Flutter apps tend to refer to the official documentation. However, in the case of React Native, you several options. You could use the official documentation or you could use a different platform, the most popular being Expo. Expo offers more features and customizations, including an integrated icon library, whereas the official React Native docs are more bare-bones.

The React Native ecosystem is more mature and has more users since JavaScript has been around since 1995. Flutter, by contrast, was released in 2017. React is probably the most popular frontend framework at the moment and has a very active community across social media. Flutter is no slouch; at the time of writing, it has more stars than React Native on GitHub.

Both Flutter and React Native have been used in popular commercial applications. Flutter was used to create the apps for Reflectly, Stadia, Baidu, Groupon, and eBay, to name a few. Meanwhile, the apps for Facebook, Instagram, Shopify, and Discord were built with React Native.

The numbers are fairly similar across social media too, with Flutter having more followers on Twitter and React Native having a larger following on Reddit.

Practical example: Developing an app with Flutter and React Native

Let’s run through some quick code examples to demonstrate how to create an app using Flutter and React Native.

Our example app is called Social and it has two screens. The iOS and Android versions look identical. The images below show how it looks on an iPhone:

Flutter React Native App Iphone Homepage

Flutter React Native App Iphone Profile

Flutter code examples

Flutter’s widget-based architecture is quite unique compared to traditional programming methodologies. Once you understand how it works, it becomes second nature.

Flutter Widget Based Architecture Folder

main.dart file

import 'package:flutter/material.dart';
import 'package:social_app/screens/home_screen.dart';
import 'package:social_app/screens/profile_screen.dart';

void main() {
  runApp(Social());
}

class Social extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      initialRoute: HomeScreen.id,
      routes: {
        HomeScreen.id: (context) => HomeScreen(),
        ProfileScreen.id: (context) => ProfileScreen(),
      },
    );
  }
}

home_screen.dart

import 'package:flutter/material.dart';
import 'package:social_app/screens/profile_screen.dart';

class HomeScreen extends StatelessWidget {
  static String id = 'home_screen';

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Color(0xffb0c1957),
      appBar: AppBar(
        toolbarHeight: 40,
        title: Text(
          'Social',
          style: TextStyle(
              color: Colors.black, fontSize: 16, fontWeight: FontWeight.bold),
        ),
        backgroundColor: Colors.white,
      ),
      body: Column(
        mainAxisAlignment: MainAxisAlignment.spaceBetween,
        children: [
          Container(
            width: 400,
            margin: EdgeInsets.only(top: 20),
            child: RaisedButton(
              color: Color(0xff23397B),
              padding: EdgeInsets.all(20),
              onPressed: () {
                Navigator.push(context,
                    MaterialPageRoute(builder: (context) => ProfileScreen()));
              },
              child: Text(
                'PROFILE',
                style:
                    TextStyle(color: Colors.white, fontWeight: FontWeight.bold),
              ),
            ),
          ),
          SizedBox(
            height: 1,
          ),
          Container(
            child: Center(
              child: Text(
                'HOME',
                style: TextStyle(
                    fontSize: 40,
                    color: Colors.white,
                    fontWeight: FontWeight.bold),
              ),
            ),
          ),
          Container(
            child: Image(
              image: AssetImage('images/home-bg.jpg'),
            ),
          ),
        ],
      ),
    );
  }
}

profile_screen.dart

import 'package:flutter/material.dart';
import 'package:social_app/screens/home_screen.dart';

class ProfileScreen extends StatelessWidget {
  static String id = 'profile_screen';

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Color(0xffb0c1957),
      appBar: AppBar(
        toolbarHeight: 40,
        title: Text(
          'Social',
          style: TextStyle(
              color: Colors.black, fontSize: 16, fontWeight: FontWeight.bold),
        ),
        backgroundColor: Colors.white,
      ),
      body: Column(
        mainAxisAlignment: MainAxisAlignment.start,
        children: [
          Container(
            width: 400,
            margin: EdgeInsets.only(top: 20),
            child: RaisedButton(
              color: Color(0xff23397B),
              padding: EdgeInsets.all(20),
              onPressed: () {
                Navigator.push(context,
                    MaterialPageRoute(builder: (context) => HomeScreen()));
              },
              child: Text(
                'HOME',
                style:
                    TextStyle(color: Colors.white, fontWeight: FontWeight.bold),
              ),
            ),
          ),
          SizedBox(
            height: 50,
          ),
          Container(
            child: Center(
              child: Text(
                'PROFILE',
                style: TextStyle(
                    fontSize: 40,
                    color: Colors.white,
                    fontWeight: FontWeight.bold),
              ),
            ),
          ),
          SizedBox(
            height: 20,
          ),
          Container(
              child: CircleAvatar(
            radius: 130.0,
            backgroundImage: AssetImage('images/profile-image.jpg'),
          )),
          SizedBox(
            height: 20,
          ),
          Container(
            child: Text(
              'SARAH TAYLOR',
              style: TextStyle(
                  color: Colors.white,
                  fontSize: 20,
                  fontWeight: FontWeight.bold),
            ),
          ),
          SizedBox(
            height: 20,
          ),
          Container(
            color: Color(0xff000d4a),
            padding: EdgeInsets.all(18.0),
            child: Container(
              child: Text(
                "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla ut ultricies velit. Proin at nisi nisl. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Etiam eu tincidunt dui. Quisque non ornare ex, facilisis congue enim. In neque nulla, posuere at gravida id, dapibus et libero.",
                style: TextStyle(
                  color: Colors.white,
                  fontSize: 17,
                ),
              ),
            ),
          )
        ],
      ),
    );
  }
}

React Native code examples

If you already know React for the web, the code here will look very familiar. The architecture for setting up a React Native project is almost the same as in React.

Project structure

React Native Code Example Project Structure

App.js

// Import statements for the components used in the app and the navigation
import React from 'react';
import { NavigationContainer } from '@react-navigation/native';
import { createStackNavigator } from '@react-navigation/stack';
const Stack = createStackNavigator();
import HomeScreen from './src/screens/HomeScreen';
import ProfileScreen from './src/screens/ProfileScreen';
// The main component with all of the screen routing business logic
const App = () => {
    return (
        <NavigationContainer>
            <Stack.Navigator initialRouteName="HomeScreen" screenOptions={{ gestureEnabled: false }}>
                <Stack.Screen name="HomeScreen" component={HomeScreen} options={{ title: 'Social' }} />
                <Stack.Screen name="ProfileScreen" component={ProfileScreen} options={{ title: 'Social' }} />
            </Stack.Navigator>
        </NavigationContainer>
    );
};
export default App;

Home.js

// Import statements for the components used in the app
import React from 'react';
import { View, Text, StyleSheet, TouchableOpacity, Image } from 'react-native';
import HomeBG from '../../assets/home-bg.jpg';
// The main component for the HomeScreen
const HomeScreen = ({ navigation }) => {
    return (
        <View style={styles.appStyle}>
            <TouchableOpacity
                style={styles.btnContainer}
                title="Profile"
                onPress={() => navigation.navigate('ProfileScreen')}
            >
                <Text style={styles.btnText}>Profile</Text>
            </TouchableOpacity>
            <Text style={styles.heading}>Home</Text>
            <View>
                <Image style={styles.homeBG} source={HomeBG} />
            </View>
        </View>
    );
};
// The component specific styles for the HomeScreen
const styles = StyleSheet.create({
    appStyle: {
        backgroundColor: 'rgb(12,25,87)',
        height: '100%',
    },
    btnContainer: {
        backgroundColor: '#23397B',
        padding: 20,
        justifyContent: 'center',
        alignItems: 'center',
        marginHorizontal: 20,
        marginVertical: 20,
    },
    btnText: {
        color: '#ffffff',
        fontWeight: 'bold',
        textTransform: 'uppercase',
    },
    heading: {
        fontSize: 40,
        color: '#ffffff',
        textAlign: 'center',
        margin: 20,
        fontWeight: 'bold',
        textTransform: 'uppercase',
    },
    homeBG: {
        height: '100%',
        width: '100%',
    },
});
export default HomeScreen;

ProfileScreen.js

// Import statements for the components used in the app
import React from 'react';
import { View, Text, StyleSheet, TouchableOpacity, Image } from 'react-native';
import ProfileImage from '../../assets/profile-image.jpg';
// The main component for the ProfileScreen
const ProfileScreen = ({ navigation }) => {
    return (
        <View style={styles.appStyle}>
            {/* TouchableOpacity is basically a more customizable button component */}
            <TouchableOpacity style={styles.btnContainer} title="Profile" onPress={() => navigation.navigate('HomeScreen')}>
                <Text style={styles.btnText}>Home</Text>
            </TouchableOpacity>
            <Text style={styles.heading}>Profile</Text>
            <View style={styles.profileContainer}>
                <Image style={styles.profileImage} source={ProfileImage} />
            </View>
            <View>
                <Text style={styles.profileName}>Sarah Taylor</Text>
            </View>
            <View style={styles.profileBioContainer}>
                <Text style={styles.profileBio}>
                    Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla ut ultricies velit. Proin at nisi nisl. Class
                    aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Etiam eu tincidunt dui.
                    Quisque non ornare ex, facilisis congue enim. In neque nulla, posuere at gravida id, dapibus et libero.
                </Text>
            </View>
        </View>
    );
};
// The component specific styles for the ProfileScreen
const styles = StyleSheet.create({
    appStyle: {
        backgroundColor: 'rgb(12,25,87)',
        height: '100%',
    },
    btnContainer: {
        backgroundColor: '#23397B',
        padding: 20,
        justifyContent: 'center',
        alignItems: 'center',
        marginHorizontal: 20,
        marginVertical: 20,
    },
    btnText: {
        color: '#ffffff',
        fontWeight: 'bold',
        textTransform: 'uppercase',
    },
    heading: {
        fontSize: 40,
        color: '#ffffff',
        textAlign: 'center',
        margin: 20,
        fontWeight: 'bold',
        textTransform: 'uppercase',
    },
    profileContainer: {
        alignItems: 'center',
    },
    profileImage: {
        borderRadius: 100,
        height: 250,
        width: 250,
    },
    profileName: {
        color: '#ffffff',
        fontSize: 20,
        textAlign: 'center',
        fontWeight: 'bold',
        margin: 20,
        textTransform: 'uppercase',
    },
    profileBioContainer: {
        backgroundColor: 'rgba(0,13,74,0.4234068627450981)',
    },
    profileBio: {
        marginHorizontal: 20,
        marginVertical: 20,
        color: '#ffffff',
        fontSize: 18,
    },
});
export default ProfileScreen;

Should you use Flutter or React Native?

There is no clear winner here: both Flutter and React have their pros and cons, and the right choice will depend on your experience and the goals and requirements of your project.

If you already know JavaScript, writing mobile apps in React Native is a no-brainer. However, if you’re looking for better performance and stability and a more cohesive environment between ecosystems, you should consider giving Flutter a try.

: Full visibility into your web apps

LogRocket is a frontend application monitoring solution that lets you replay problems as if they happened in your own browser. Instead of guessing why errors happen, or asking users for screenshots and log dumps, LogRocket lets you replay the session to quickly understand what went wrong. It works perfectly with any app, regardless of framework, and has plugins to log additional context from Redux, Vuex, and @ngrx/store.

In addition to logging Redux actions and state, LogRocket records console logs, JavaScript errors, stacktraces, network requests/responses with headers + bodies, browser metadata, and custom logs. It also instruments the DOM to record the HTML and CSS on the page, recreating pixel-perfect videos of even the most complex single-page apps.

.
Andrew Baisden I’m a full-stack developer from London. Programming is one of my passions in life. A majority of my most recent skills have been self-taught. I find this is one of the best ways to learn because you can go at your own pace.

2 Replies to “Flutter vs. React Native”

  1. Hey I would have to say that React Native is my favorite at the moment. I am more familiar with the codebase and the ecosystem is more mature. However I see Flutter becoming more dominant in the future.

Leave a Reply