struct MyComponent: View {
var displayString: String
var body: some View {
Text(displayString)
}
}














Compare Declarative Frameworks





class MyComponent extends StatelessWidget {
final String displayString;
MyComponent({required this.displayString});
Widget build(BuildContext context) {
return Text(displayString);
}
}
function MyComponent(props) {
return <div>{props.displayString}</div>;
}
struct ConditionalComponent: View {
let condition: Bool
var body: some View {
Group {
if condition {
Text("Condition is true")
} else {
Text("Condition is false")
}
}
}
}
// Usage
ConditionalComponent(condition: true)
class ConditionalComponent extends StatelessWidget {
final bool condition;
ConditionalComponent({required this.condition});
Widget build(BuildContext context) {
if(condition) {
return Text("Condition is true");
} else {
return Text("Condition is false");
}
}
}
// Usage
ConditionalComponent(condition: true)
function ConditionalComponent({ condition }) {
return (
<>
{condition ? (
<p>Condition is true</p>
) : (
<p>Condition is false</p>
)}
</>
);
}
// Usage
<ConditionalComponent condition={true} />;
struct Parent: View {
let data: String
var body: some View {
IntermediateComponent(data: data)
}
}
struct IntermediateComponent: View {
let data: String
var body: some View {
ChildComponent(data: data)
}
}
struct ChildComponent: View {
let data: String
var body: some View {
Text("Received data: \(data)")
}
}
// Usage
Parent(data: "Some data")
class Parent extends StatelessWidget {
final String data;
Parent({required this.data});
Widget build(BuildContext context) {
return IntermediateComponent(data: data);
}
}
class IntermediateComponent extends StatelessWidget {
final String data;
IntermediateComponent({required this.data});
Widget build(BuildContext context) {
return ChildComponent(data: data);
}
}
class ChildComponent extends StatelessWidget {
final String data;
ChildComponent({required this.data});
Widget build(BuildContext context) {
return Text("Received data: $data");
}
}
// Usage
Parent(data: "Some data")
function Parent({ data }) {
return <IntermediateComponent data={data} />;
}
function IntermediateComponent({ data }) {
return <ChildComponent data={data} />;
}
function ChildComponent({ data }) {
return <p>Received data: {data}</p>;
}
// Usage
<Parent data="Some data" />;
struct ClickableComponent: View {
@State private var clicked = false
var body: some View {
Button(action: {
clicked = true
}) {
Text(clicked ? "Button clicked" : "Click me")
}
}
}
class ClickableComponent extends StatefulWidget {
_ClickableComponentState createState() => _ClickableComponentState();
}
class _ClickableComponentState extends State<ClickableComponent> {
bool clicked = false;
Widget build(BuildContext context) {
return RaisedButton(
onPressed: () => setState(() => clicked = true),
child: Text(clicked ? "Button clicked" : "Click me"),
);
}
}
import { useState } from "react";
function ClickableComponent() {
const [clicked, setClicked] = useState(false);
return (
<button onClick={() => setClicked(true)}>
{clicked ? "Button clicked" : "Click me"}
</button>
);
}
struct TextInputComponent: View {
@State private var text = ""
var body: some View {
TextField("Enter text", text: $text)
}
}
class TextInputComponent extends StatefulWidget {
const TextInputComponent({super.key});
State<TextInputComponent> createState() => _TextInputComponentState();
}
class _TextInputComponentState extends State<TextInputComponent> {
late final _controller = TextEditingController(text: "");
void dispose() {
_controller.dispose();
super.dispose();
}
Widget build(BuildContext context) {
return TextField(
controller: _controller,
decoration: const InputDecoration(labelText: "Enter text"),
);
}
}
function TextInputComponent() {
const [text, setText] = useState("");
return (
<input
type="text"
value={text}
onChange={(e) => setText(e.target.value)}
placeholder="Enter text"
/>
);
}
struct ExampleComponent: View {
var body: some View {
Text("Hello, World!")
}
}
struct ExampleComponent_Previews: PreviewProvider {
static var previews: some View {
ExampleComponent()
}
}
Flutter doesn't have a built-in preview feature. You can, however, create a separate app or run your app in an emulator or on a device to view your components. Additionally, you can use the Flutter Studio web-based tool to create and preview Flutter widgets in a browser.
React doesn't have a built-in preview feature. However, you can use a tool like Storybook to create previews for your components in a separate development environment.
struct ListComponent: View {
let items: [String]
var body: some View {
List(items, id: \.self) { item in
Text(item)
}
}
}
// Usage
let items = ["Item 1", "Item 2", "Item 3"]
ListComponent(items: items)
class ListComponent extends StatelessWidget {
final List<String> items;
ListComponent({required this.items});
Widget build(BuildContext context) {
return ListView.builder(
itemCount: items.length,
itemBuilder: (context, index) {
return ListTile(title: Text(items[index]));
},
);
}
}
// Usage
final items = ["Item 1", "Item 2", "Item 3"];
ListComponent(items: items)
function ListComponent({ items }) {
return (
<ul>
{items.map((item) => (
<li key={item}>{item}</li>
))}
</ul>
);
}
// Usage
const items = ["Item 1", "Item 2", "Item 3"];
<ListComponent items={items} />;
struct Person: Identifiable {
let name: String
let age: Int
let id: String
}
struct ItemKeysExample: View {
let items: [Person]
var body: some View {
List(items) { person in
Text("Name: \(person.name), Age: \(person.age)")
}
}
}
// Usage
ItemKeysExample(items: [Person(name: "John", age: 30, id: "1"), Person(name: "Jane", age: 28, id: "2"), Person(name: "Bob", age: 25, id: "3")])
class Person {
final String name;
final int age;
final String id;
Person({required this.name, required this.age, required this.id});
}
class ItemKeysExample extends StatelessWidget {
final List<Person> items;
ItemKeysExample({required this.items});
Widget build(BuildContext context) {
return ListView.builder(
itemCount: items.length,
itemBuilder: (context, index) {
final person = items[index];
return ListTile(
key: Key(person.id),
title: Text('Name: ${person.name}, Age: ${person.age}'),
);
},
);
}
}
// Usage
ItemKeysExample(items: [Person(name: 'John', age: 30, id: '1'), Person(name: 'Jane', age: 28, id: '2'), Person(name: 'Bob', age: 25, id: '3')])
function ItemKeysExample({ items }) {
return (
<ul>
{items.map((person) => (
<li key={person.id}>
Name: {person.name}, Age: {person.age}
</li>
))}
</ul>
);
}
// Usage
<ItemKeysExample
items={[
{ name: "John", age: 30, id: "1" },
{ name: "Jane", age: 28, id: "2" },
{ name: "Bob", age: 25, id: "3" },
]}
/>;
struct Parent<Header: View, Content: View>: View {
let header: Header
let content: Content
var body: some View {
VStack {
header
content
}
}
}
// Usage
Parent(
header: Text("Header"),
content: Child()
)
struct Child: View {
var body: some View {
Text("Child Content")
}
}
class Parent extends StatelessWidget {
final Widget header;
final Widget content;
Parent({required this.header, required this.content});
Widget build(BuildContext context) {
return Column(
children: [
header,
content,
],
);
}
}
// Usage
Parent(
header: Text("Header"),
content: Child(),
)
class Child extends StatelessWidget {
Widget build(BuildContext context) {
return Text("Child Content");
}
}
function Parent({ header, content }) {
return (
<div>
{header}
{content}
</div>
);
}
// Usage
<Parent header={<h1>Header</h1>} content={<Child />} />;
function Child() {
return <p>Child Content</p>;
}
struct ModifiersExample: View {
var body: some View {
Text("Hello, World!")
.padding(EdgeInsets(top: 16, leading: 16, bottom: 16, trailing: 16))
.background(Color.blue)
}
}
In Flutter, you can wrap widgets with other widgets to achieve similar effects.
class ModifiersExample extends StatelessWidget {
Widget build(BuildContext context) {
return Container(
padding: EdgeInsets.all(16.0),
color: Colors.blue,
child: Text('Hello, World!', style: TextStyle(color: Colors.white)),
);
}
}
React doesn't have a direct analog to modifiers in Jetpack Compose or SwiftUI. Instead, you can use inline styles or CSS classes.
function ModifiersExample() {
const style = {
padding: "16px",
backgroundColor: "blue",
color: "white",
};
return <div style={style}>Hello, World!</div>;
}
struct Counter: View {
@State private var count = 0
var body: some View {
Button(action: {
count += 1
}) {
Text("Count: \(count)")
}
}
}
class Counter extends StatefulWidget {
_CounterState createState() => _CounterState();
}
class _CounterState extends State<Counter> {
int count = 0;
Widget build(BuildContext context) {
return RaisedButton(
onPressed: () => setState(() => count += 1),
child: Text("Count: $count"),
);
}
}
import { useState } from "react";
function Counter() {
const [count, setCount] = useState(0);
return (
<button onClick={() => setCount(count + 1)}>
Count: {count}
</button>
);
}
struct CustomEnvironmentKey: EnvironmentKey {
static let defaultValue: String = ""
}
extension EnvironmentValues {
var customData: String {
get { self[CustomEnvironmentKey.self] }
set { self[CustomEnvironmentKey.self] = newValue }
}
}
struct Parent: View {
let data: String
var body: some View {
Intermediate().environment(\.customData, data)
}
}
struct Intermediate: View {
var body: some View {
Child()
}
}
struct Child: View {
@Environment(\.customData) private var data
var body: some View {
Text("Received data: \(data)")
}
}
// Usage
Parent(data: "Some data")
class CustomInheritedWidget extends InheritedWidget {
final String data;
CustomInheritedWidget({required this.data, required Widget child})
: super(child: child);
bool updateShouldNotify(CustomInheritedWidget oldWidget) {
return oldWidget.data != data;
}
static CustomInheritedWidget of(BuildContext context) {
return context.dependOnInheritedWidgetOfExactType<CustomInheritedWidget>()!;
}
}
class Parent extends StatelessWidget {
final String data;
Parent({required this.data});
Widget build(BuildContext context) {
return CustomInheritedWidget(
data: data,
child: Intermediate(),
);
}
}
class Intermediate extends StatelessWidget {
Widget build(BuildContext context) {
return Child();
}
}
class Child extends StatelessWidget {
Widget build(BuildContext context) {
final data = CustomInheritedWidget.of(context).data;
return Text("Received data: $data");
}
}
// Usage
Parent(data: "Some data")
import { createContext, useContext } from "react";
const CustomContext = createContext();
function Parent({ data }) {
return (
<CustomContext.Provider value={data}>
<Intermediate />
</CustomContext.Provider>
);
}
function Intermediate() {
return <Child />;
}
function Child() {
const data = useContext(CustomContext);
return <p>Received data: {data}</p>;
}
// Usage
<Parent data="Some data" />;
struct SideEffectOnLoadComponent: View {
@State private var hasPerformedSideEffect = false
var body: some View {
if !hasPerformedSideEffect {
DispatchQueue.main.async {
// Perform side effect, e.g. fetch data, update external data source
hasPerformedSideEffect = true
}
}
// Other UI components
Text("Hello, World!")
}
}
class SideEffectOnLoadComponent extends StatefulWidget {
_SideEffectOnLoadComponentState createState() => _SideEffectOnLoadComponentState();
}
class _SideEffectOnLoadComponentState extends State<SideEffectOnLoadComponent> {
void initState() {
super.initState();
// Perform side effect, e.g. fetch data, update external data source
}
Widget build(BuildContext context) {
// Other UI components
return Container();
}
}
import { useEffect } from "react";
function SideEffectOnLoadComponent() {
useEffect(() => {
// Perform side effect, e.g. fetch data, update external data source
}, []);
// Other UI components
return <div />;
}
Frequently Asked Questions About SwiftUI vs Flutter vs React
Which is better for beginners, SwiftUI or Flutter or React?
Let's analyze the learning curve and requirements for each framework in 2025:
SwiftUI (4/5)
SwiftUI offers an intuitive approach for iOS development with excellent documentation and powerful preview features. While it requires understanding Swift and iOS concepts, its declarative syntax and strong type system help catch errors early and make the development process more predictable.
Learning Path:
- Master Swift basics (especially protocols and property wrappers)
- Understand iOS app architecture
- Learn SwiftUI view hierarchy and data flow
- Practice with property wrappers and state management
- Explore SwiftUI's animation system
Key Prerequisites:
- Swift
- iOS development concepts
- Xcode
Time to Productivity: 2-3 months for iOS developers, 4-5 months for beginners
React (4/5)
React's component-based architecture and extensive ecosystem make it accessible for beginners. While concepts like hooks and virtual DOM require time to master, the large community and abundance of learning resources help overcome challenges. TypeScript adoption adds type safety but increases the initial learning curve.
Learning Path:
- Learn modern JavaScript/TypeScript
- Understand React components and JSX
- Master hooks and state management
- Learn component lifecycle and effects
- Practice React patterns and best practices
Key Prerequisites:
- JavaScript/TypeScript
- HTML/CSS
- npm/yarn
Time to Productivity: 2-3 months for web developers, 3-4 months for beginners
Flutter (3/5)
Flutter requires learning Dart, which may be unfamiliar to many developers. However, its comprehensive documentation, hot reload feature, and widget-based architecture make the learning process systematic. The consistent behavior across platforms reduces platform-specific complexity.
Learning Path:
- Learn Dart programming language
- Understand Flutter widget system
- Master state management approaches
- Learn platform integration techniques
- Practice responsive design patterns
Key Prerequisites:
- Dart
- Basic programming concepts
- Mobile UI principles
Time to Productivity: 3-4 months for mobile developers, 4-6 months for beginners
Recommendation
Based on the analysis, SwiftUI offers the most approachable learning curve. However, your choice should depend on:
- Your existing programming background (Swift, Dart, JavaScript/TypeScript)
- Target platform requirements (iOS, Cross-platform, Cross-platform)
- Available learning time (2-3 months for iOS developers, 4-5 months for beginners for SwiftUI)
- Long-term career goals in mobile/web development
How does the performance of SwiftUI compare to Flutter in real-world applications?
Let's analyze the real-world performance characteristics of SwiftUI and Flutter based on benchmarks and practical experience:
SwiftUI Performance Profile
Strengths
-
✓ Efficient diffing algorithm
Uses a sophisticated diffing algorithm to minimize view updates and maintain smooth performance.
-
✓ Native platform optimization
Direct integration with Apple's rendering engine provides excellent performance on iOS devices.
-
✓ Automatic memory management
Swift's ARC (Automatic Reference Counting) ensures efficient memory usage.
Areas for Optimization
-
! List performance issues
Complex lists with dynamic content can experience performance degradation.
-
! State propagation overhead
Deep view hierarchies with frequent state updates can impact performance.
Flutter Performance Profile
Strengths
-
✓ Custom rendering engine
Skia rendering engine provides consistent performance across platforms without relying on native components.
-
✓ Widget tree optimization
Efficient widget rebuilding system that minimizes the impact of UI updates.
-
✓ JIT/AOT compilation
Supports both Just-in-Time compilation for development and Ahead-of-Time compilation for release builds.
Areas for Optimization
-
! Initial app size
Larger app size due to bundled runtime and engine components.
-
! Complex screen jank
Can experience frame drops on screens with complex animations or heavy computation.
Performance Optimization Tips
SwiftUI
- Use @StateObject for expensive objects that need to persist
- Implement lazy loading with LazyVStack and LazyHStack
- Leverage SwiftUI's built-in performance tools
- Profile with Instruments to identify bottlenecks
Flutter
- Use const constructors for static widgets
- Implement proper keys in lists for efficient updates
- Leverage Flutter's built-in performance overlay
- Profile with DevTools to identify performance bottlenecks
What are the key architectural differences between SwiftUI and Flutter and React?
Here are the key differences between SwiftUI and Flutter and React:
Feature | SwiftUI | Flutter | React |
---|---|---|---|
Paradigm | Declarative UI framework with a protocol-oriented approach | Declarative UI toolkit with a widget-based approach | Declarative UI library with a component-based approach |
Target Platform | Apple platforms (iOS, macOS, watchOS, tvOS) | Cross-platform (iOS, Android, web, desktop) | Web (with React Native for mobile) |
Language | Swift | Dart | JavaScript/TypeScript |
Component Model | View protocol conforming structs | Widget classes (stateless and stateful) | Function components with hooks or class components |
State Management | Property wrappers (@State, @Binding, @ObservedObject) | StatefulWidget with setState, or state management packages | useState, useReducer, and third-party solutions like Redux |
Ecosystem | Tightly integrated with Apple's development ecosystem | Google-backed with a growing ecosystem of packages | Vast ecosystem with many libraries and tools |
The choice between these frameworks often depends on your target platform, existing expertise, and specific project requirements. SwiftUI and Flutter and React each have their strengths in different contexts.
What are the job market trends for SwiftUI vs Flutter vs React in 2025?
If you're considering a career move in 2025, here's how these frameworks compare in terms of job prospects:
SwiftUI
- Current Demand: Increasing as iOS apps adopt the newer framework
- Growth Trajectory: Steady growth as Apple continues to enhance capabilities
- Notable Companies: Apple, Uber, Lyft, Airbnb
Flutter
- Current Demand: High demand for cross-platform development skills
- Growth Trajectory: One of the fastest-growing mobile frameworks
- Notable Companies: Google, Alibaba, BMW, eBay
React
- Current Demand: Very high demand across web, mobile (React Native), and desktop
- Growth Trajectory: Mature but still growing with continuous innovation
- Notable Companies: Meta, Netflix, Airbnb, Dropbox
Flutter offers the advantage of cross-platform skills, while native frameworks like SwiftUI may provide deeper platform integration. Many companies value developers who can work in both worlds.
Can SwiftUI and Flutter and React be used together in the same project?
Understanding how SwiftUI and Flutter and React can work together:
SwiftUI + Flutter
SwiftUI can be integrated with Flutter through platform channels, allowing you to use native iOS functionality within a Flutter app.
SwiftUI + React
React (via React Native) can use SwiftUI through native modules, though this is complex and not typically recommended.
Flutter + React
Flutter and React/React Native are separate frameworks. While both can be used in the same project (e.g., Flutter for one feature, React Native for another), this is uncommon and complex.
Using multiple frameworks: While it's technically possible to use SwiftUI, Flutter, React in a single project ecosystem, this adds complexity. It's generally better to choose the right tool for each platform and maintain consistency within that platform.
Web + Mobile Strategy: A common approach is to use React for your web application, while using SwiftUI or Flutter for mobile apps. You can share business logic and API calls between them, but the UI layer would be implemented separately for each platform.
Is Flutter better than SwiftUI for app development?
The choice between Flutter and SwiftUI depends on your project requirements:
Aspect | Flutter | SwiftUI |
---|---|---|
Platform Support | iOS, Android, Web, Windows, macOS, Linux | iOS, macOS, watchOS, tvOS |
Native Integration | Good via platform channels, but not direct | Excellent native platform integration |
Performance | Very good with custom rendering engine | Excellent on target platform |
Development Speed | Fast with hot reload and single codebase | Fast for its target platform |
UI Consistency | Same UI across all platforms | Platform-specific UI with native feel |
Choose Flutter if:
- You need to support multiple platforms with one codebase
- UI consistency across platforms is more important than native platform feel
- You want to reduce development and maintenance costs
- Your team can focus on learning one technology stack (Dart)
Choose SwiftUI if:
- You're only targeting Apple platforms
- Deep platform integration is critical for your app
- You want the most native feel and performance
- Your team already has expertise in Swift
Many companies use both approaches: Flutter for cross-platform features and SwiftUI for platform-specific features that require deeper integration.
Why does Flutter use Dart instead of a more common language?
Flutter's choice of Dart as its programming language offers several technical advantages:
- Just-in-Time (JIT) compilation during development enables hot reload, allowing for quick iteration
- Ahead-of-Time (AOT) compilation for releases creates high-performance native code
- Non-blocking asynchronous programming through async/await and Future objects
- Sound null safety helps eliminate null reference errors
- Fast garbage collection optimized for UI construction patterns
- Object-oriented with mixins for reusable code
While languages like JavaScript or Kotlin might have larger communities, Dart was specifically optimized for Flutter's needs in building reactive UIs and achieving native performance. Google has invested heavily in making Dart an excellent language for UI development.
Despite being less common, Dart is easy to learn for developers familiar with Java, JavaScript, or C#, with most developers becoming productive within a few weeks.