Quick Answer
React Native is a framework that lets you write one JavaScript or TypeScript codebase and ship it as a genuine native app on both iOS and Android. You write your app once, and it produces the same kind of app you would get from a dedicated Swift team and a dedicated Kotlin team, from a single shared codebase.
Left: a single dark jumpsuit hanging alone: one cohesive piece. Right: four separate garments laid flat: each independent and swappable. Monolith vs capsule wardrobe.
One codebase, two platforms. React Native is the capsule wardrobe of mobile development: one shared foundation, dressed appropriately for each platform.

The problem: two platforms, two languages

Every smartphone runs one of two operating systems: Apple’s iOS or Google’s Android. These platforms are entirely separate, built by competing companies, and they use different programming languages.

  • iOS is written in Swift (or older Objective-C). Native iOS apps are built in Xcode on a Mac.
  • Android is written in Kotlin (or older Java). Native Android apps are built in Android Studio.

For a company that wants an app on both platforms, the traditional approach means:

  • Two separate teams (or one team switching between two languages)
  • Two codebases to maintain for every feature and bug fix
  • Two different release processes, two sets of platform quirks to learn

This doubles the cost of mobile development. For a startup or a small engineering team, native apps on both platforms was often simply not feasible.

React Native’s solution

React Native (released by Meta/Facebook in 2015) lets you write your app once in JavaScript or TypeScript, the same language used for web development, and deploy it to both platforms.

The pitch: one codebase, two real native apps.

Not one app that runs in a web browser embedded in a shell (that older approach, called a hybrid or WebView app, always felt slow and slightly wrong). React Native renders actual native UI components on each platform.

How it actually works

This is where people often get confused, so it is worth being precise.

What “native” means

A native app uses the UI building blocks that the operating system provides. On iOS, these are UIKit components: UILabel (text), UIButton (buttons), UIScrollView (scrollable lists). On Android, they are Material components: TextView, Button, RecyclerView.

When these components are used, they look exactly right on the platform, because they are the platform’s own components. The system animations, the scrolling physics, the font rendering, the accessibility layer, all of it is the real thing.

A web-in-a-shell approach (WebView) renders HTML and CSS inside a browser widget embedded in the app. It can look almost native, but the scrolling feels different, text rendering is subtly wrong, and performance suffers for complex interactions.

The bridge (old architecture)

In the original React Native design, your JavaScript code and the native platform ran in separate threads. To get a message from one to the other, say, “create a button at position X with this label”, React Native used an asynchronous bridge: a message queue between JavaScript and native code, serialised as JSON.

This worked well for most apps but introduced latency for interactions that required very fast back-and-forth between JavaScript and native (gesture-driven animations, for example).

The new architecture: JSI and Fabric

Since 2022, React Native has been migrating to a new architecture that eliminates the bridge:

  • JSI (JavaScript Interface): a C++ layer that lets JavaScript call native functions directly, synchronously, without serialisation. No message queue, no JSON overhead.
  • Fabric: a reimplemented rendering layer that can synchronously compute layouts and respond to gestures without crossing a thread boundary.

The practical result: the new architecture closes roughly 90% of the performance gap between React Native and fully native apps. Since Expo SDK 53 (2025), the new architecture is enabled by default for new projects.

Your Code
TypeScript / JavaScript React components Business logic
React Native Runtime
Hermes JS Engine JSI (direct native calls) Fabric Renderer
Platform Native Layer
iOS: UIKit / Swift Android: Jetpack / Kotlin

The React component model

If you have used React for web, React Native will feel familiar. You build UIs by composing components, functions that describe what should appear on screen.

The difference is the component names. On the web you write <div>, <p>, <button>. In React Native:

Web (React)React NativeWhat it is
<div><View>A container / layout box
<p>, <span><Text>Any visible text (must use this)
<button><Pressable>Tappable element
<img><Image>Image display
<ul> with items<FlatList>Scrollable list (virtualised)
<input><TextInput>Text entry field

Every piece of visible text in React Native must be wrapped in a <Text> component. Putting raw text outside a <Text> is a runtime error. (This feels strict at first; you get used to it.)

A simple screen component:

tsx
import { View, Text, Pressable, StyleSheet } from "react-native";

export default function WelcomeScreen() {
  return (
    <View style={styles.container}>
      <Text style={styles.heading}>Hello, world</Text>
      <Pressable style={styles.button} onPress={() => console.log("tapped")}>
        <Text style={styles.buttonText}>Tap me</Text>
      </Pressable>
    </View>
  );
}

const styles = StyleSheet.create({
  container: { flex: 1, alignItems: "center", justifyContent: "center" },
  heading: { fontSize: 24, fontWeight: "bold", marginBottom: 16 },
  button: { backgroundColor: "#0070f3", padding: 12, borderRadius: 8 },
  buttonText: { color: "white", fontWeight: "600" },
});

Layout uses flexbox, the same model as CSS but with different defaults. flex: 1 means “take up all available space”. flexDirection defaults to column (unlike the web, which defaults to row).

Performance: how close to native?

React Native gets asked about performance constantly. The honest answer in 2026:

  • For the vast majority of apps, content feeds, forms, e-commerce, dashboards, chat, React Native performance is indistinguishable from native to users.
  • The new architecture (JSI + Fabric) eliminated the serialisation overhead that caused visible lag in the old bridge model.
  • For graphics-intensive apps, games, video editing, AR filters, complex data visualisations at 120fps, native Swift or Kotlin (or Flutter, which has its own renderer) may be preferable.

The 90% benchmark: React Native covers 90% of apps without noticeable trade-offs. The remaining 10% needs native code.

When to use what

SituationRecommended approach
New app, team knows JavaScript/TypeScriptReact Native (via Expo)
App requires heavy graphics, AR, or game-like UINative (Swift + Kotlin) or Flutter
Team is fluent in Dart, app needs pixel-perfect cross-platform UIFlutter
App is mostly informational, can run in a browserProgressive Web App (PWA)
Existing native codebase, adding JS screens graduallyReact Native (brownfield integration)
Maximum iOS performance, Apple-specific features (ARKit, CoreML on-device)Native Swift

React Native vs Flutter: a fair comparison

React NativeFlutter
LanguageJavaScript / TypeScriptDart
RenderingPlatform’s own native componentsFlutter draws its own pixels (Skia/Impeller)
Cross-platform consistencyUI adapts to each platform’s styleIdentical UI on both platforms (by default)
EcosystemVery large (npm, React community)Growing fast (pub.dev)
PerformanceExcellent for most appsExcellent, especially for animations
Learning curveLow if you know JavaScriptModerate (Dart is new for most)
BackingMeta (open-source)Google (open-source)

Neither is objectively better. If your team already knows JavaScript, React Native’s onramp is faster. If you need pixel-perfect cross-platform consistency and smooth animations on first launch, Flutter is worth the Dart investment.

How to get started

The standard starting point is Expo, which wraps React Native in a cohesive toolkit with a managed build service and a curated SDK. You do not need Xcode or Android Studio to run your first app, Expo Go (a free app on your phone) runs it instantly during development.

bash
# Create a new app
npx create-expo-app@latest my-app

# Start the development server
cd my-app
npx expo start

# Scan the QR code with Expo Go on your phone

See the Expo tool article for the full build pipeline, SDK modules, and how OTA updates work.

See also
  • Expo : the toolkit that makes React Native practical. Managed builds, OTA updates, a curated SDK, file-based routing.
  • Zustand : the state management library recommended for React Native. Minimal, TypeScript-native, works with AsyncStorage out of the box.
  • AsyncStorage : on-device key-value storage. Persists Zustand state across app restarts.
  • From Zero to Production : how React Native fits into a complete production architecture, from demo to deployed app.

Further reading

What’s next

Next: Expo, the React Native framework that handles the hard parts , covering the build pipeline, SDK modules, and how to get an app to the App Store without owning a Mac.