Every mobile project eventually faces this question: do we build natively for iOS and Android separately, or do we use a cross-platform framework? The answer is not always obvious, and the wrong choice can cost you months of rework. Here is how we think about it after 15 years of building mobile apps.
The Options in 2025
The landscape has evolved significantly. These are the realistic options today:
- Fully native (iOS + Android separate): Swift/SwiftUI (Xcode) for iOS, Kotlin/Jetpack Compose (Android Studio) for Android. Maximum control, maximum quality, maximum cost.
- Kotlin Multiplatform (KMP): Shared business logic in Kotlin, native UI on each platform. Best of both worlds for projects with significant shared logic.
- Flutter: Shared Dart codebase, custom rendering engine. Fast to develop, but the UI is never truly native.
- React Native: Shared JavaScript/TypeScript codebase, native component bridge. Large ecosystem, but the bridge adds complexity and performance overhead.
When to Go Fully Native
Fully separate native codebases make sense when:
- The app is deeply platform-specific. An app built around Apple Watch, ARKit or HealthKit has no meaningful Android counterpart. Build native iOS only.
- Performance is critical. Real-time audio processing, high-frame-rate graphics, BLE-intensive hardware communication — all are easier to optimize when you control every layer.
- The platforms serve different user bases. Sometimes the iOS and Android versions of a product are genuinely different enough that sharing code creates more friction than it saves.
- You have separate iOS and Android teams already. If you have skilled native developers for each platform, full native development is often the right choice.
When to Use Kotlin Multiplatform
KMP is a strong choice when:
- You need both platforms and the app has significant business logic (API clients, data models, offline sync, caching).
- You want native UI on both platforms — no compromises on look, feel or platform conventions.
- You have an existing Android Kotlin codebase and need to add iOS support.
- Your team knows Kotlin and is willing to learn SwiftUI (or vice versa).
KMP gives you the maintainability benefits of a shared codebase without sacrificing the native UI layer. The shared Kotlin module is a standard Android library from Android Studio’s perspective, and a native Swift framework from Xcode’s perspective.
When Flutter or React Native Make Sense
Flutter and React Native are best when:
- Speed to market is the primary constraint and a working prototype matters more than polish.
- The app is primarily content-driven (news, e-commerce, CRUD operations) with minimal platform-specific features.
- Your team is already proficient in Dart (Flutter) or React/JavaScript (React Native) and retraining is not feasible.
- The visual design is custom enough that platform conventions don’t apply (games, heavily branded apps).
The honest trade-off: Flutter and React Native let you move faster early, but you will eventually hit platform limitations that require native code bridges, platform-specific workarounds, or full rewrites of specific features. Budget for this.
The Hardware Integration Factor
If your app needs to talk to hardware — BLE devices, LoRaWAN gateways, NFC tags, custom USB peripherals — native or KMP is almost always the right choice. Hardware integrations rely on low-level platform APIs that cross-platform frameworks expose imperfectly or not at all. The BLE stack on iOS (CoreBluetooth) and Android behave differently, and these differences cannot be abstracted away cleanly by a framework layer.
Our Recommendation
If you need both iOS and Android, are serious about quality, and the app has meaningful business logic: choose Kotlin Multiplatform. If you only need one platform, or the app is very platform-specific: go fully native. If time-to-market is the primary driver and quality is secondary: Flutter or React Native.
Every project is different. We are happy to walk through your specific requirements and give you a concrete recommendation. Get in touch.

No responses yet