Débutant60 min40 XP
Objectifs de cette leçon
- Créer des composants réutilisables
- Comprendre les props et leur transmission
- Concevoir une hiérarchie de composants
Composants React Native 📱
Les composants natifs sont les briques de construction de ton app. Contrairement au web où on a des balises HTML (div, p, button), React Native a ses propres composants qui deviennent de vrais éléments natifs iOS/Android !
1. Les composants de base 🧱
text ' View = le conteneur de base (comme <div> en HTML) ' Text = pour afficher du texte (comme <p>) ' StyleSheet = pour styliser (comme CSS) ``'
import { View, Text, StyleSheet } from "react-native"; function CarteBienvenue() { return ( <View style={styles.carte}> <Text style={styles.titre}>Bienvenue !</Text> <Text style={styles.sousTitre}>React Native c'est génial</Text> </View> ); } const styles = StyleSheet.create({ carte: { backgroundColor: "#fff", borderRadius: 12, padding: 20, margin: 10, // shadow = ombre (comme boxShadow en CSS) shadowColor: "#000", shadowOffset: { width: 0, height: 2 }, shadowOpacity: 0.1, shadowRadius: 4, elevation: 3, // Pour Android }, titre: { fontSize: 24, fontWeight: "bold", color: "#333", }, sousTitre: { fontSize: 16, color: "#666", marginTop: 8, }, });
3. TouchableOpacity et TextInput 👆
import { View, Text, TextInput, TouchableOpacity, StyleSheet } from "react-native"; function FormulaireConnexion() { const [email, setEmail] = React.useState(""); const [motDePasse, setMotDePasse] = React.useState(""); const handleConnexion = () => { console.log("Connexion avec", email, motDePasse); }; return ( <View style={styles.container}> <Text style={styles.titre}>Connexion</Text> <TextInput style={styles.input} placeholder="Email" value={email} onChangeText={setEmail} keyboardType="email-address" autoCapitalize="none" /> <TextInput style={styles.input} placeholder="Mot de passe" value={motDePasse} onChangeText={setMotDePasse} secureTextEntry // ← cache le texte ! /> <TouchableOpacity style={styles.bouton} onPress={handleConnexion}> <Text style={styles.boutonTexte}>Se connecter</Text> </TouchableOpacity> </View> ); } ``' --- ## 4. Image et ScrollView 🖼️ ```tsx import { Image, ScrollView, View, Text, StyleSheet } from "react-native"; function GaleriePhotos() { const photos = [ { id: "1", url: "https://picsum.photos/200/300", titre: "Paysage 1" }, { id: "2", url: "https://picsum.photos/200/300", titre: "Paysage 2" }, { id: "3", url: "https://picsum.photos/200/300", titre: "Paysage 3" }, ]; return ( <ScrollView style={styles.container}> {photos.map((photo) => ( <View key={photo.id} style={styles.carte}> <Image source={{ uri: photo.url }} style={styles.image} resizeMode="cover" /> <Text style={styles.titre}>{photo.titre}</Text> </View> ))} </ScrollView> ); } ``' --- ## 5. FlatList — la liste performante 📋 ```text ' FlatList = la liste ULTRA performante de React Native ' Pourquoi ? Elle ne charge QUE les éléments visibles à l'écran ! ' (C'est ce qu'on appelle la virtualisation) ' ScrollView = charge TOUT d'un coup → lent si beaucoup d'éléments ' FlatList = charge seulement ce qui est visible → rapide même avec 10 000 items ``' ```tsx import { FlatList, Text, View, StyleSheet } from "react-native"; interface Utilisateur { id: number; nom: string; email: string; } function ListeUtilisateurs() { const [utilisateurs, setUtilisateurs] = React.useState<Utilisateur[]>([]); const [chargement, setChargement] = React.useState(true); React.useEffect(() => { fetch("https://jsonplaceholder.typicode.com/users") .then((res) => res.json()) .then((data) => { setUtilisateurs(data); setChargement(false); }); }, []); const renderItem = ({ item }: { item: Utilisateur }) => ( <View style={styles.item}> <Text style={styles.nom}>{item.nom}</Text> <Text style={styles.email}>{item.email}</Text> </View> ); return ( <FlatList data={utilisateurs} renderItem={renderItem} keyExtractor={(item) => item.id.toString()} refreshing={chargement} onRefresh={() => {/* recharger */}} /> ); } const styles = StyleSheet.create({ item: { padding: 16, borderBottomWidth: 1, borderColor: "#eee" }, nom: { fontSize: 18, fontWeight: "600" }, email: { fontSize: 14, color: "#666" }, }); ``' --- ## 6. Différences iOS vs Android 🍎🤖 ```tsx import { Platform, SafeAreaView, StatusBar, StyleSheet } from "react-native"; // Platform.OS permet d'adapter le comportement const styles = StyleSheet.create({ container: { paddingTop: Platform.OS === "ios" ? 44 : StatusBar.currentHeight, // iOS : 44px pour la safe area // Android : hauteur de la barre de statut }, }); function MonApp() { return ( <SafeAreaView style={styles.container}> {/* SafeAreaView = évite la zone de la notch iOS */} <StatusBar barStyle="dark-content" /> </SafeAreaView> ); } ``' --- ## Exercices pour toi 🎯 1. **Carte profil** : crée un composant `CarteProfil` avec Image, Text, et TouchableOpacity qui affiche "Bonjour {nom}" quand on clique 2. **Liste de tâches** : utilise FlatList pour afficher une liste de tâches avec TextInput pour en ajouter de nouvelles 3. **Adaptation plateforme** : crée un composant qui affiche "🍎 iOS" sur iPhone et "🤖 Android" sur Android avec Platform.OS
Création des variables pas à pas
Prêt à explorer la mémoire
Appuie sur Play pour voir les variables se créer une par une
0/5
Visualisation d'exécution
ligne 17code
1type ProfilProps = {
2 nom: string;
3 age: number;
4};
5
6function Profil({ nom, age }: ProfilProps) {
7 return (
8 <View>
9 <Text style={{ fontSize: 20 }}>{nom}</Text>
10 <Text>{age} ans</Text>
11 </View>
12 );
13}
14
15function App() {
16 return (
17 <View style={{ flex: 1 }}>
18 <Profil nom="Alice" age={25} />
19 <Profil nom="Bob" age={17} />
20 </View>
21 );
22}
Variables
App.rendu=<View> → 2×<Profil>
Profil.props.nom=Alice | Bob
Profil.props.age=25 | 17
🌳 Arbre de composants
📱 App
📐 Header
Logo
Menu
📋 Contenu
Carte×3
👤 Footer
Crédits
📦 Flux des Props
Clique pour avancer le flux
⚡ Simulateur — Composants React Native
Étape 1/8📝 Pseudo-code
1// Composition de composants
2type ProfilProps = { nom: string; age: number };
3
4function Profil({ nom, age }: ProfilProps) { # ⬅ composant
5 return (
6 <View style={{ padding: 12 }}>
7 <Text style={{ fontSize: 20, fontWeight: 'bold' }}> # ⬅ nom
8 {nom}
9 </Text>
10 <Text>{age} ans</Text> # ⬅ âge
11 </View>
12 );
13}
14
15function App() {
16 return (
17 <View style={{ flex: 1 }}>
18 <Profil nom='Alice' age={25} /> # ⬅ réutilisé
19 <Profil nom='Bob' age={17} /> # ⬅ réutilisé
20 </View>
21 );
22}
🧱 Composition RN
💡 Composition
- Les props transmettent les données du parent à l'enfant
- Un composant = une brique réutilisable
- Même composant + props différentes = affichages différents
La composition est le coeur de React Native : on crée des petits composants réutilisables.