0% ont trouvé ce document utile (0 vote)
28 vues83 pages

Flutter 2

Le document présente une introduction à Flutter, en détaillant les composants essentiels pour construire une application, tels que MaterialApp, Scaffold, AppBar, Drawer, BottomNavigationBar, TabBar et des widgets de disposition comme Column, Row et Stack. Chaque composant est accompagné de ses propriétés et d'exemples de code pour illustrer leur utilisation. L'accent est mis sur la structuration, la navigation et la disposition des éléments dans une application Flutter.

Transféré par

louraknouhaila
Copyright
© © All Rights Reserved
Nous prenons très au sérieux les droits relatifs au contenu. Si vous pensez qu’il s’agit de votre contenu, signalez une atteinte au droit d’auteur ici.
Formats disponibles
Téléchargez aux formats DOCX, PDF, TXT ou lisez en ligne sur Scribd
0% ont trouvé ce document utile (0 vote)
28 vues83 pages

Flutter 2

Le document présente une introduction à Flutter, en détaillant les composants essentiels pour construire une application, tels que MaterialApp, Scaffold, AppBar, Drawer, BottomNavigationBar, TabBar et des widgets de disposition comme Column, Row et Stack. Chaque composant est accompagné de ses propriétés et d'exemples de code pour illustrer leur utilisation. L'accent est mis sur la structuration, la navigation et la disposition des éléments dans une application Flutter.

Transféré par

louraknouhaila
Copyright
© © All Rights Reserved
Nous prenons très au sérieux les droits relatifs au contenu. Si vous pensez qu’il s’agit de votre contenu, signalez une atteinte au droit d’auteur ici.
Formats disponibles
Téléchargez aux formats DOCX, PDF, TXT ou lisez en ligne sur Scribd

Flutter

✅ Frontend (UI/UX, animations, responsive design)

✅ Backend & API (Firebase, REST, GraphQL)

✅ Gestion de données (SQLite, Hive, Firebase Firestore)

✅ Performance & Optimisation

✅ Sécurité & Authentification

✅ Tests & Déploiement

✅ Hardware & IoT (Bluetooth, NFC, capteurs)

Ces widgets définissent la structure d’une application Flutter.

Structure et Mise en Page

MaterialApp :

📌 Intérêt : placé en haut de l'arbre des widgets -> c le widget racine dans les appli flutter

🔹 Propriétés : home, theme, title, routes, debugShowCheckedModeBanner, initialRoute.

home : Le widget affiché au démarrage de l'application. C'est le premier écran que l'utilisateur verra.

theme : Permet de définir un thème global pour l'application, qui affecte l'apparence de tous les
widgets Material.

title : le titre de l'application

routes : permet de definir un ensemble de routes pour la navigation chaque route correspond a un

widget specifique a afficher

debugShowCheckedModeBanner : Permet d'afficher ou de masquer le "debug banner" (le petit


message "DEBUG" en haut à droite)

initialRoute : définie la route initial a utiliser lorsequ'une application est lancée .

import 'package:flutter/[Link]';

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

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp (

title: 'Exemple de MaterialApp', // Définir le titre de l'application


theme: ThemeData ( // Définir le thème global de l'application

primarySwatch: [Link],

visualDensity: [Link],

),

initialRoute: '/home', // Définir la route initiale de l'application

routes: { // Définir les routes de navigation

'/home': (context) => HomePage(),

'/details': (context) => DetailsPage(),

},

debugShowCheckedModeBanner : false, // Afficher ou non le "debug banner"

home: HomePage(), // L'écran principal affiché au démarrage

); //materialApp

class HomePage extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold (

appBar: AppBar( title: Text ('Page d\'Accueil') ) ,

body: Center (

child: ElevatedButton (

onPressed: () { [Link](context, '/details'); // Navigation vers la page } ,

child : Text ( 'Aller à la page de détails'), ) ,

),//center ) ;//scaffold } }

class DetailsPage extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold (

appBar: AppBar ( title: Text('Page de Détails') ) ,

body: Center ( child: Text (' Bienvenue dans la page de détails ! '), ), //center ) ; //scaffold } }

Scaffold
📌 Intérêt : pour de structurer une page web ca veut dire mis le header , body , footer.

🔹 Propriétés : appBar, body, floatingActionButton, bottomNavigationBar, drawer ,backgroundColor.

appBar :barre d'application en haut de l'ecran.

body : le contenu principal de la page.

floatingActionButton : bouton flottant pour les actions spécifiques.

bottomNavigationBar : barre de navigation en bas de page

drawer : c l'icone de humburger pour les menu latéral

import 'package:flutter/[Link]';

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

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp ( home: HomePage(), ) ;

class HomePage extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold (

appBar: AppBar ( title : Text (' Exemple de Scaffold '), backgroundColor : [Link], ) ,

drawer: Drawer ( // Menu latéral

child: ListView (

padding: [Link],

children: <Widget> [

DrawerHeader ( decoration: BoxDecoration ( color: [Link], ), child: Text (' Menu '), ),

ListTile ( title : Text ('Option 1'), onTap: () {}, ),

ListTile ( title: Text('Option 2'), onTap: () {}, ),

], ), //listview ), //drawer

body : Center ( child: Text (' Bienvenue dans l\'application Flutter! '), ),

floatingActionButton: FloatingActionButton (
onPressed : () { print('Bouton flottant cliqué!'); },

child : Icon( [Link] ),

),

bottomNavigationBar: BottomNavigationBar (

items: [

BottomNavigationBarItem ( icon: Icon([Link]), label: 'Accueil', ),

BottomNavigationBarItem ( icon: Icon([Link]), label: 'Paramètres', ),

],

onTap: (index) { print ('L\'élément sélectionné: $index') ; } ,

), //bottomNavigationBar ) ; //scaffold } }

AppBar

📌 Intérêt : c le header qui existe dans le haut de l'ecran

🔹 Propriétés : theme ,title,routes , actions, backgroundColor, leading


theme : définir un thème spécifique pour l'AppBar. Cela peut inclure des modifications de couleurs, polices, etc.

title : Le texte qui apparaîtra comme titre de l'AppBar. Généralement, il décrit la page ou l'écran actuel.

routes : afficher des actions pour naviguer entre les écrans .

actions : liste de widgets à afficher à droite de l'AppBar. Par exemple, des icônes de notifications, des menus, ou
des boutons d'action.

backgroundColor : définir la couleur de fond de l'AppBar.

leading : widget affiché à gauche de l'AppBar, souvent un bouton de retour ou une icône de menu (par exemple,
un hamburger menu).

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp( home: HomePage(), );

class HomePage extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold (

appBar : AppBar (

title : Text(' Page d\'Accueil '),


actions : [

IconButton (

icon: Icon( [Link] ),

onPressed: () { print('Recherche lancée'); },

),

],

backgroundColor: [Link],

// Définir un widget à gauche de l'AppBar (exemple : un bouton de menu)

leading: IconButton (

icon: Icon([Link]),
onPressed: () { print('Menu ouvert'); },

),

), //appBar

body: Center ( child: Text (' Bienvenue dans la page d\'accueil '), ),

); } }

Drawer
📌 Intérêt : Crée un menu latéral (comme un menu hamburger).

🔹 Propriétés : child, elevation, scrimColor.

child : contenu du menu

elevation : definir l'ombre du drawer plus la valeur st élevée , plus l',ombre est forte ce qui donne
l'illusion de profondeur

scrimColor : Définit la couleur de l'ombre qui apparaît sur le reste de l'écran lorsque le Drawer est
ouvert. Cela aide à se concentrer sur le menu et à flouter l'arrière-plan.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp ( home : HomePage(), ) ; } }

class HomePage extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold (

appBar : AppBar ( title: Text (' Page avec Drawer ') , ),

drawer : Drawer (
elevation : 16.0, // Ombre de l'effet du Drawer

scrimColor : [Link](0.5), // Couleur de l'ombre derrière le Drawer

child: ListView (

padding : [Link],

children : <Widget> [

DrawerHeader (

decoration : BoxDecoration ( color : [Link], ),

child: Text (

'Menu Principal',

style: TextStyle ( color: [Link] , fontSize: 24, ),

),

),

ListTile (

title : Text(' Page 1 '),

onTap: () {

print('Page 1 sélectionnée');

[Link](context); // Fermer le Drawer

},

),

ListTile (

title : Text(' Page 2 '),

onTap: () {

print('Page 2 sélectionnée');

[Link](context); }, // Fermer le Drawer

), ], ), ),

body: Center ( child: Text(' Contenu de la page '), ),

); } }

BottomNavigationBar

📌 Intérêt : Barre de navigation en bas.

🔹 Propriétés : items, currentIndex, onTap

items : Une liste d'éléments de navigation, Chaque élément a un icône et un texte associés.

currentIndex : L'indice de l'élément actuellement sélectionné. Cela permet de savoir quelle page est
active.
onTap : Une fonction de rappel qui est appelée lorsque l'utilisateur sélectionne un élément dans la
barre de navigation.

Cela permet de changer l'écran ou effectuer des actions en fonction de l'élément sélectionné.

class MyApp extends StatefulWidget {

@override

_MyAppState createState() => _MyAppState();

class _MyAppState extends State<MyApp> {

int _currentIndex = 0; // Indice de l'élément sélectionné

final List<Widget> _pages = [

Center ( child : Text (' Page 1 ') ),

Center ( child : Text (' Page 2 ') ),

Center ( child : Text (' Page 3 ') ),

];

void _onItemTapped(int index) {

setState ( () {

_currentIndex = index; // Met à jour l'indice de l'élément sélectionné

} );

@override

Widget build(BuildContext context) {

return MaterialApp (

home: Scaffold (

appBar: AppBar ( title : Text (' Barre de Navigation Inférieure '), ),

body : _pages[_currentIndex], // Affiche la page en fonction de l'indice actuel

bottomNavigationBar : BottomNavigationBar (

currentIndex : _currentIndex, // Indicateur de l'élément sélectionné

onTap : _onItemTapped, // Action lors de la sélection d'un élément

items : const <BottomNavigationBarItem> [

BottomNavigationBarItem ( icon : Icon([Link]), label: 'Accueil', ),


BottomNavigationBarItem ( icon : Icon([Link]), label: 'Recherche', ),

BottomNavigationBarItem ( icon : Icon ([Link]), label: 'Notifications', ),

],

),//bottomNavigationBar

), //scaffold

) ; //MaterialApp

TabBar & TabBarView


📌 Intérêt : Gérer plusieurs pages avec des onglets.

🔹 Propriétés : tabs, controller, children

tabs (TabBar) : La liste des onglets à afficher. Chaque onglet est généralement un widget Tab, avec un
texte ou une icône.

controller (TabBar et TabBarView) : Le contrôleur qui permet de gérer l'état des onglets et de
synchroniser TabBar et TabBarView. Il est typiquement de type TabController.

children (TabBarView) : La liste des widgets qui sont affichés lorsque chaque onglet est sélectionné.
Chaque enfant correspond à une page différente.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp (

home : DefaultTabController (

length : 3, // Le nombre d'onglets

child : Scaffold (

appBar: AppBar (

title : Text (' Exemple TabBar & TabBarView '),

bottom : TabBar (

tabs: [

Tab(text: 'Onglet 1'),


Tab(text: 'Onglet 2'),

Tab(text: 'Onglet 3'),

],

), //fin de tabBar

), //fin de AppBar

Body : TabBarView (

children: [

Center ( child : Text (' Contenu de l\'Onglet 1 ') ),

Center ( child : Text (' Contenu de l\'Onglet 2 ') ),

Center ( child : Text (' Contenu de l\'Onglet 3 ') ),

],

), //TabBarView

) , //Scaffold

), //DefaultTabController

) ; //MaterialApp

Disposition des Éléments

Ces widgets organisent les éléments sur l’écran.

Column

📌 Intérêt : Dispose les widgets verticalement.

🔹 Propriétés : children, mainAxisAlignment, crossAxisAlignment

children : Liste des widgets que la Column va disposer verticalement.

mainAxisAlignment : Permet de définir l'alignement des éléments le long de l'axe principal (vertical).
Par exemple, vous pouvez centrer, espacer ou aligner en haut ou en bas.

crossAxisAlignment : Permet de définir l'alignement des éléments le long de l'axe transversal


(horizontal), c'est-à-dire la direction perpendiculaire à l'axe principal.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp (
home : Scaffold (

appBar: AppBar ( title: Text('Exemple de Column'), ),

body : Column (

mainAxisAlignment: [Link], // Centrer verticalement

crossAxisAlignment: [Link], // Aligner à gauche horizontalement

children: <Widget> [

Text('Premier élément'),

Text('Deuxième élément'),

ElevatedButton (

onPressed: () {},

child : Text (' Troisième élément' ),

),

],

), //column

), //scaffold

) ; //MaterialApp

Row

📌 Intérêt : Dispose les widgets horizontalement.

🔹 Propriétés : children, mainAxisAlignment, crossAxisAlignment

children : Liste des widgets que le Row va disposer horizontalement.

mainAxisAlignment : Permet de définir l'alignement des éléments le long de l'axe principal


(horizontal).

crossAxisAlignment : Permet de définir l'alignement des éléments le long de l'axe transversal


(vertical), c'est-à-dire la direction perpendiculaire à l'axe principal.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp (
home : Scaffold (

appBar : AppBar ( title: Text(' Exemple de Row '), ),

body: Row (

mainAxisAlignment: [Link], // Espacement égal entre les éléments

crossAxisAlignment: [Link], // Centrer verticalement

children: <Widget> [

Icon([Link]),

Icon([Link]),

Icon([Link]),

],

), //row

), //Scaffold

) ; //MaterialApp

Stack

📌 Intérêt : Superpose plusieurs widgets.

🔹 Propriétés : children, alignment, fit

children : Liste des widgets à superposer. Les éléments sont ajoutés à la pile dans l'ordre où ils sont
définis, le dernier élément étant placé au-dessus des précédents.

alignment : Définit l'alignement des éléments à l'intérieur du Stack. Par exemple, vous pouvez choisir
de centrer les éléments ou de les placer en haut à gauche.

fit : Contrôle la façon dont les enfants sont dimensionnés. Il existe deux options :

[Link] (par défaut) : Les enfants peuvent être dimensionnés librement.

[Link] : Les enfants remplissent toute la taille disponible du Stack.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {


return MaterialApp (

home : Scaffold (

appBar: AppBar ( title: Text('Exemple de Stack'), ),

body: Stack (

alignment : [Link], // Centrer les enfants dans le Stack

children: <Widget> [

Container ( width: 200, height: 200, color: [Link], ),

Positioned (

top: 30,

child: Container(width: 100, height: 100, color: [Link], ),

),

Positioned (

bottom: 30,

child: Container(width: 50, height: 50, color: [Link], ),

),

],

), //Stack

), //scaffold

) ; //MaterialApp

+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Exemple avancé : Création d'une image avec du texte par-dessus

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Stack(

children: <Widget>[

[Link]('path_to_image.jpg'),

Positioned(

bottom: 20,

left: 20,

child: Text(
'Texte superposé sur l\'image',

style: TextStyle(color: [Link], fontSize: 24),

), ), ], )

Expanded

📌 Intérêt : Permet à un widget de prendre tout l’espace disponible.

🔹 Propriétés : child, flex

child : Le widget qui sera "étendu" pour occuper l'espace disponible. Le child est l'élément à
l'intérieur de Expanded qui sera ajusté.

flex : Un entier qui définit la proportion d'espace que cet Expanded doit occuper par rapport aux
autres Expanded dans le même parent. Par défaut, il est égal à 1, mais vous pouvez augmenter ou
diminuer cette valeur pour changer la proportion d'espace occupée.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp (

home : Scaffold (

appBar : AppBar( title: Text('Exemple de Expanded'), ),

body : Row (

children : <Widget> [

Expanded (

Flex : 2, // Prend deux fois plus d'espace que le deuxième Expanded

child : Container (

color: [Link],

height : 100,

child : Center ( child: Text(' Élément 1 ') ),

),

),

Expanded (

Flex : 1, // Prend une proportion plus petite de l'espace

child : Container (

color: [Link],

height: 100,

child: Center(child: Text('Élément 2')),


), //container

), //Expanded

],

), //Row

), //Scaffold

) ; //MaterialApp

+++++++++++++++++++++++++++++++++++++++++++

Exemple Avancé : Utiliser Expanded dans une colonne pour un espace flexible

Column(

children: <Widget>[

Container(

color: [Link],

height: 50,

child: Center(child: Text('Header')),

),

Expanded(

child: Container(

color: [Link],

child: Center(child: Text('Contenu flexible')),

),

),

Container(

color: [Link],

height: 50,

child: Center(child: Text('Footer')),

),

],

10. Wrap
📌 Intérêt : Organise les widgets dans une grille de manière dynamique

🔹 Propriétés : children, alignment, spacing ,runSpacing

children : Liste des widgets à afficher dans le Wrap. Ce sont les éléments qui seront disposés
automatiquement dans la grille.

alignment : Permet de définir l'alignement des widgets dans chaque ligne ou colonne (par exemple,
[Link], [Link], etc.).

spacing : Espace entre les widgets dans une même ligne (horizontalement, si c'est une disposition
horizontale).

runSpacing : Espace entre les lignes ou colonnes de widgets (verticalement, si c'est une disposition
verticale).

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp (

home : Scaffold (

appBar : AppBar ( title: Text('Exemple de Wrap'), ),

body : Padding (

padding : [Link](10),

child : Wrap (

alignment: [Link], // Aligne les widgets au centre

spacing: 10, // Espace entre les éléments sur la même ligne

runSpacing: 20, // Espace entre les lignes

children: <Widget> [

Container (

color: [Link],

width: 100,

height: 100,

child: Center(child: Text('Élément 1')),

),

Container(

color: [Link],
width: 100,

height: 100,

child: Center(child: Text('Élément 2')),

),

Container(

color: [Link],

width: 100,

height: 100,

child: Center(child: Text('Élément 3')),

),

Container(

color: [Link],

width: 100,

height: 100,

child: Center(child: Text('Élément 4')),

), ], ), ), ), ) ; } }

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Exemple Avancé : Utiliser Wrap pour une grille dynamique

+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Wrap(

spacing: 10.0, // Espace entre les éléments horizontaux

runSpacing: 10.0, // Espace entre les lignes

children: [Link](10, (index) {

return Container(

width: 100,

height: 100,

color: [Link][index % [Link]], // Utilisation de couleurs aléatoires

child: Center(child: Text('Item $index')),

); } ), )
Widgets d’Affichage

Ces widgets permettent d’afficher du contenu.

11. Container

📌 Intérêt : Ajoute un fond, un padding, une marge et une taille.

🔹 Propriétés : width, height, color, padding, margin, decoration , child

width : Définit la largeur du Container.

height : Définit la hauteur du Container.

color : Spécifie la couleur de fond du Container.

padding : Ajoute un espacement à l'intérieur du Container entre le contenu (comme un texte, une
image, etc.) et les bords du Container.

margin : Définit un espace extérieur autour du Container, en créant de l'espace entre le Container et
les autres éléments voisins.

decoration : Permet d'ajouter des éléments de décoration comme des bordures, des coins arrondis,
des ombres, etc.

child : Contient un autre widget enfant (par exemple, un Text, Icon, ou même un autre widget
Container).

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple de Container'),

),

body: Center(

child: Container(

width: 200, // Largeur du Container

height: 100, // Hauteur du Container

color: [Link], // Fond bleu

padding: [Link](20), // Padding de 20 pixels à l'intérieur


margin: [Link](horizontal: 40, vertical: 20), // Marge

decoration: BoxDecoration(

borderRadius: [Link](10), // Coins arrondis

boxShadow: [

BoxShadow(

color: [Link](0.3), // Ombre subtile

offset: Offset(4, 4), // Déplacement de l'ombre

blurRadius: 5, // Flou de l'ombre

),

],

),

child: Center(

child: Text(

'Bonjour, Flutter!',

style: TextStyle(color: [Link], fontSize: 18),

), ), ), ), ), ) ; } }

++++++++++++++++++++++++++++++++++++++++++++

Exemple Avancé : Utiliser Container pour une Carte avec Bordure et Ombre

++++++++++++++++++++++++++++++++++++++++++++++

Container(

width: 300,

height: 200,

padding: [Link](16),

margin: [Link](20),

decoration: BoxDecoration(

color: [Link],

borderRadius: [Link](15),

border: [Link](color: [Link], width: 2), // Bordure bleue

boxShadow: [

BoxShadow(

color: [Link](0.2), // Ombre légère


blurRadius: 10,

offset: Offset(0, 4), // Ombre portée vers le bas

),

],

),

child: Column(

mainAxisAlignment: [Link],

children: <Widget>[

Text(

'Titre de la carte',

style: TextStyle(fontSize: 24, fontWeight: [Link]),

),

SizedBox(height: 10),

Text('Contenu de la carte avec une bordure et une ombre'),

], ), )

12. Padding

📌 Intérêt : Ajoute un padding autour de son enfant

🔹 Propriétés : padding, child

padding : Définit la quantité d'espacement (padding) autour de l'enfant. Il prend généralement un


objet EdgeInsets pour spécifier les valeurs de padding (par exemple, à gauche, à droite, en haut et en
bas).

child : Le widget enfant à l'intérieur du Padding. C'est ce widget qui bénéficiera de l'espacement
défini.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple de Padding'), ),

body: Center(

child: Padding(
padding: [Link](20), // Espacement de 20 pixels autour de l'enfant

child: Container(

color: [Link],

child: Text(

'Texte avec Padding',

style: TextStyle(color: [Link], fontSize: 20),

), ), ), ), ), ) ; } }

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Exemple Avancé : Padding avec Espacement Différent sur Chaque Côté

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Padding(

padding: [Link](top: 50, left: 20, right: 20), // Espacement différent pour chaque côté

child: Container(

color: [Link],

child: Text(

'Padding personnalisé',

style: TextStyle(fontSize: 18, color: [Link]),

), ), )

SizedBox

📌 Intérêt : Définit un espace vide ou une taille fixe.

🔹 Propriétés : width, height, child

child : Le widget enfant à l'intérieur du SizedBox. Si aucun enfant n'est fourni, cela crée simplement
un espace vide de la taille spécifiée

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple de SizedBox'),

),
body: Column(

mainAxisAlignment: [Link],

children: <Widget>[

Text('Premier texte'),

SizedBox(height: 20), // Espace de 20 pixels entre les éléments

Text('Deuxième texte'),

SizedBox(width: 100), // Espace horizontal de 100 pixels

Container(

color: [Link],

width: 100,

height: 100,

child: Text('Contenu dans un Container'),

), ], ), ), ) ; } }

+++++++++++++++++++++++++++++++++++++++++

Exemple Avancé : SizedBox avec un Child

+++++++++++++++++++++++++++++++++++++++++++++

SizedBox(

height: 50, // Hauteur fixe

child: ElevatedButton(

onPressed: () {},

child: Text('Bouton avec taille fixe'),

),

14. Divider

📌 Intérêt : Affiche une ligne de séparation.

🔹 Propriétés : height, color, thickness

height : Définit la hauteur de l'espace autour du Divider (espace vertical avant et après la ligne). Ce
n'est pas la hauteur de la ligne elle-même, mais de l'espace qu'elle occupe.
color : Permet de définir la couleur de la ligne de séparation. Par défaut, il est gris.

thickness : Définit l'épaisseur de la ligne. Par défaut, l'épaisseur est de 0.5 pixels.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple de Divider'),

),

body: Column(

children: <Widget>[

ListTile(

title: Text('Élément 1'),

),

Divider(

height: 20, // Espace avant et après la ligne

color: [Link], // Couleur de la ligne

thickness: 2, // Épaisseur de la ligne

),

ListTile(

title: Text('Élément 2'),

),

Divider(

height: 30,

color: [Link],

thickness: 1,

),

ListTile(

title: Text('Élément 3'),

), ], ), ), ) ; } }
Card

📌 Intérêt : Affiche un contenu avec une ombre et des bordures.

🔹 Propriétés : elevation, color, shape, child

elevation : Détermine l'élévation de la carte, c'est-à-dire la hauteur de l'ombre portée. Une valeur
plus élevée crée une ombre plus importante, rendant la carte plus proéminente sur l'écran.

color : Permet de définir la couleur de fond de la carte. Par défaut, la couleur est blanche.

shape : Permet de définir la forme des bords de la carte. Par exemple, on peut l'arrondir ou lui
donner un aspect rectangulaire avec des coins droits.

child : Le widget enfant à l'intérieur de la carte. Il peut être tout type de widget (textes, images,
boutons, etc.).

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple de Card'),

),

body: Center(

child: Card(

elevation: 8, // Ombre plus marquée

color: [Link][100], // Couleur de fond de la carte

shape: RoundedRectangleBorder(

borderRadius: [Link](15), // Coins arrondis

),

child: Padding(

padding: const [Link](16.0),

child: Column(

children: <Widget>[

Text(

'Titre de la Carte',

style: TextStyle(fontSize: 20, fontWeight: [Link]),


),

SizedBox(height: 10),

Text(

'Ceci est un exemple de contenu à l\'intérieur de la carte. Vous pouvez ajouter plus
d\'éléments ici.',

style: TextStyle(fontSize: 16),

), ], ), ), ), ), ), ) ; } }

FlatButton

📌 Intérêt : Un bouton sans élévation, souvent pour des actions secondaires.

🔹 Propriétés : onPressed, child, color, shape.

onPressed : Fonction qui est exécutée lorsque le bouton est pressé. C'est ici que vous définissez
l'action à accomplir lorsque l'utilisateur clique sur le bouton.

child : Contenu du bouton, généralement un Text ou une Icon qui décrit l'action du bouton.

color : Permet de définir la couleur de fond du bouton. Par défaut, elle est souvent transparente, mais
vous pouvez la personnaliser.

shape : Permet de personnaliser la forme du bouton. Par exemple, vous pouvez arrondir les bords du
bouton ou le rendre rectangulaire.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple de FlatButton'),

),

body: Center(

child: FlatButton(

onPressed: () {

// Action à exécuter lorsque le bouton est pressé

print('FlatButton pressé!');

},
child: Text(

'Appuyez ici',

style: TextStyle(color: [Link]), // Couleur du texte

),

color: [Link], // Couleur du fond

shape: RoundedRectangleBorder(

borderRadius: [Link](10), // Coins arrondis

), ), ), ), ) ; } }

13. Icon

📌 Intérêt : Affiche une icône.

🔹 Propriétés : icon, size, color.

icon : L'icône à afficher. Vous devez fournir un IconData (par exemple, [Link], [Link]).

size : Taille de l'icône. Par défaut, l'icône est de taille standard, mais vous pouvez ajuster sa taille avec
cette propriété.

color : Couleur de l'icône. Vous pouvez personnaliser la couleur de l'icône selon le thème de votre
application ou une couleur spécifique.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple d\'Icon'),

),

body: Center(

child: Icon(

[Link], // Icône de la maison

size: 50, // Taille de l'icône

color: [Link], // Couleur de l'icône


), ), ), ) ; } }

++++++++++++++++++++++++++++++++++

Exemple de Widget avec Icon :

++++++++++++++++++++++++++++++++++

IconButton(

icon: Icon(

[Link], // Icône des paramètres

size: 30, // Taille de l'icône

color: [Link], // Couleur de l'icône

),

onPressed: () {

print('Paramètres pressés');

}, )

24. CircularProgressIndicator

📌 Intérêt : Affiche un indicateur de progression circulaire (chargement).

🔹 Propriétés : value, color, backgroundColor.

value : Représente la progression de l'indicateur. La valeur doit être un nombre compris entre 0.0
(aucune progression) et 1.0 (progression complète). Si cette propriété n'est pas définie, l'indicateur
sera en mode indéfini, c'est-à-dire qu'il tournera en boucle sans fin jusqu'à ce que la tâche soit
terminée.

color : La couleur de l'indicateur de progression. Par défaut, elle est gris, mais vous pouvez
personnaliser la couleur selon le thème ou vos préférences.

backgroundColor : La couleur de l'arrière-plan de l'indicateur de progression. Cela est utile pour


mieux distinguer l'indicateur de progression sur des arrière-plans colorés

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(
appBar: AppBar(

title: Text('Exemple CircularProgressIndicator'),

),

body: Center(

child: CircularProgressIndicator(

value: null, // Chargement indéfini

color: [Link], // Couleur de l'indicateur

backgroundColor: [Link], // Couleur de l'arrière-plan

), ), ), ) ; } }

++++++++++++++++++++++

Exemple avec value :

++++++++++++++++++++++

CircularProgressIndicator(

value: 0.7, // Indicateur de progression à 70%

color: [Link], // Couleur de l'indicateur

backgroundColor: [Link], // Couleur de l'arrière-plan

25. LinearProgressIndicator

📌 Intérêt : Affiche un indicateur de progression linéaire.

🔹 Propriétés : value, color, backgroundColor.

value : Représente la progression de l'indicateur sous forme de valeur allant de 0.0 à 1.0. Si la valeur
est null, l'indicateur sera en mode indéfini, c'est-à-dire qu'il continuera à se remplir sans fin jusqu'à ce
qu'une tâche soit terminée.

color : La couleur de la barre de progression. Vous pouvez personnaliser la couleur pour correspondre
au thème de votre application.

backgroundColor : La couleur de l'arrière-plan de la barre de progression. Cela permet de mieux


différencier l'indicateur sur des arrière-plans de différentes couleurs.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(
appBar: AppBar(

title: Text('Exemple LinearProgressIndicator'),

),

body: Center(

child: LinearProgressIndicator(

value: null, // Chargement indéfini

color: [Link], // Couleur de la barre de progression

backgroundColor: [Link], // Couleur de l'arrière-plan

), ), ), ) ; } }

++++++++++++++++++++++

Exemple avec value :

+++++++++++++++++++++++

LinearProgressIndicator(

value: 0.5, // Indicateur de progression à 50%

color: [Link], // Couleur de la barre de progression

backgroundColor: [Link], // Couleur de l'arrière-plan

Listes et Grilles

Affichent des collections d’éléments.

16. ListView

📌 Intérêt : Affiche une liste scrollable.

🔹 Propriétés : children, scrollDirection, shrinkWrap , itemCount, itemBuilder

children : Une liste des éléments (widgets) qui composent la liste. Chaque élément de la liste est un
widget, et vous pouvez les organiser dans un tableau. Cela est généralement utilisé pour les petites
listes statiques.

scrollDirection : Définit la direction du défilement. Il peut être [Link] (par défaut) pour une liste
verticale ou [Link] pour une liste horizontale.

shrinkWrap : Si cette propriété est définie sur true, le ListView s'ajustera à la taille de son contenu,
plutôt que de s'étendre pour occuper tout l'espace disponible. Cela peut être utile pour optimiser les
performances dans certaines situations où le contenu est petit et ne nécessite pas d'optimisation de
mémoire.

itemCount : Le nombre total d'éléments à afficher dans la liste. Cette propriété est utilisée pour les
listes générées dynamiquement, comme lorsque vous récupérez des données d'une API.

itemBuilder : Une fonction qui construit chaque élément de la liste en fonction de l'index de
l'élément. Cette fonction est appelée pour chaque élément que vous souhaitez afficher dans la liste.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple ListView'),

),

body: ListView(

scrollDirection: [Link], // Liste verticale

shrinkWrap: true, // Ajuste la taille de la liste au contenu

itemCount: 5, // Nombre d'éléments

itemBuilder: (context, index) {

return ListTile(

title: Text('Élément ${index + 1}'),

); }, ), ), ) ; } }

++++++++++++++++++++++++++++++++++++++++++

Exemple avec des données dynamiques :

++++++++++++++++++++++++++++++++++

[Link](

itemCount: 10, // Nombre d'éléments dans la liste

itemBuilder: (context, index) {

return ListTile(

title: Text('Élément numéro $index'),


subtitle: Text('Sous-titre $index'),

);

},

17. GridView

📌 Intérêt : Affiche des éléments en grille.

🔹 Propriétés : gridDelegate, children

gridDelegate : Cette propriété définit la manière dont la grille est structurée. Elle prend généralement
un objet SliverGridDelegate, tel que SliverGridDelegateWithFixedCrossAxisCount ou
SliverGridDelegateWithMaxCrossAxisExtent, qui permet de spécifier le nombre de colonnes ou la
taille maximale des éléments dans la grille.

children : Une liste de widgets qui seront affichés dans la grille. Chaque élément est affiché dans une
cellule de la grille.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple GridView'),

),

body: GridView(

gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(

crossAxisCount: 3, // 3 colonnes dans la grille

crossAxisSpacing: 10, // Espacement horizontal entre les éléments

mainAxisSpacing: 10, // Espacement vertical entre les éléments

),

children: [Link](6, (index) {

return Card(

color: [Link],
child: Center(

child: Text('Élément $index', style: TextStyle(color: [Link])),

), ) ; }), ), ), ) ; } }

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Exemple avec SliverGridDelegateWithMaxCrossAxisExtent

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

GridView(

gridDelegate: SliverGridDelegateWithMaxCrossAxisExtent(

maxCrossAxisExtent: 200, // Largeur maximale des éléments dans la grille

crossAxisSpacing: 10, // Espacement horizontal

mainAxisSpacing: 10, // Espacement vertical

),

children: [Link](10, (index) {

return Card(

color: [Link],

child: Center(

child: Text('Élément $index', style: TextStyle(color: [Link])),

),

);

}), )

Widgets de Texte et Boutons

Widgets interactifs et affichage de texte.

Text

📌 Intérêt : Affiche du texte.

🔹 Propriétés : style, textAlign, overflow, maxLines

style : Permet de personnaliser l'apparence du texte. Cela inclut des propriétés comme la fontSize,
fontWeight, color, fontFamily, etc. Vous pouvez utiliser TextStyle pour personnaliser le style du texte.

textAlign : Définit l'alignement du texte. Il peut prendre les valeurs suivantes :


[Link]

[Link]

[Link]

[Link]

overflow : Définit ce qui se passe lorsque le texte déborde de son conteneur. Vous pouvez utiliser des
valeurs comme :

[Link] (ajoute des points de suspension)

[Link] (fait fondre le texte excédentaire)

[Link] (coupe simplement le texte excédentaire)

maxLines : Permet de définir le nombre maximal de lignes pour le texte. Si le texte dépasse ce
nombre, il sera coupé.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple Text Widget'),

),

body: Center(

child: Text(

'Bienvenue sur Flutter!',

style: TextStyle(

fontSize: 24, // Taille du texte

fontWeight: [Link], // Poids du texte

color: [Link], // Couleur du texte

),

textAlign: [Link], // Alignement du texte

overflow: [Link], // Gestion du débordement


maxLines: 2, // Nombre maximum de lignes

), ) , ), ) ; } }

TextField

📌 Intérêt : Champ de saisie.

🔹 Propriétés : controller, keyboardType, obscureText, decoration, onChanged

controller : Permet de contrôler et de lire la valeur du texte dans le champ de saisie. C'est un objet de
type TextEditingController.

keyboardType : Définit le type de clavier qui s'affichera pour la saisie (par exemple, clavier
numérique, texte, email, etc.). Vous pouvez utiliser des valeurs comme :

[Link] (clavier normal)

[Link] (clavier numérique)

[Link] (clavier pour email)

[Link] (clavier pour téléphone)

obscureText : Permet de masquer le texte saisi, idéal pour les champs de mot de passe. Si défini sur
true, le texte sera masqué (ex. "••••••").

decoration : Permet de personnaliser l'apparence du champ de texte, comme la bordure, le label, les
icônes, etc. Vous pouvez utiliser un InputDecoration pour ajouter des éléments comme des labels,
des icônes, des bordures.

onChanged : Un callback qui est appelé chaque fois que la valeur du texte change. Vous pouvez
utiliser cela pour mettre à jour l'état de votre application en fonction du texte saisi.

class MyApp extends StatelessWidget {

final TextEditingController _controller = TextEditingController();

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(
title: Text('Exemple TextField Widget'),

),

body: Padding(

padding: const [Link](16.0),

child: Column(

children: [

TextField(

controller: _controller,

keyboardType: [Link], // Affiche un clavier spécifique pour les emails

obscureText: false, // Texte visible, pas caché

decoration: InputDecoration(

labelText: 'Email', // Label au-dessus du champ

hintText: 'Entrez votre email', // Texte d'exemple dans le champ

border: OutlineInputBorder(), // Bordure autour du champ

),

onChanged: (text) {

print('Texte saisi: $text');

},

),

SizedBox(height: 20),

ElevatedButton(

onPressed: () {

print('Email soumis: ${_controller.text}');

},

child: Text('Soumettre'),

), ], ), ), ), ) ; } }

ElevatedButton

📌 Intérêt : Bouton standard avec une élévation visuelle.

🔹 Propriétés : onPressed, child, style


onPressed : Cette propriété définit une fonction qui est appelée lorsque le bouton est pressé. C'est un
callback obligatoire qui contient l'action à effectuer.

child : Contenu du bouton, généralement un widget comme Text, Icon, ou un autre widget
personnalisé. Cela définit ce que l'utilisateur verra à l'intérieur du bouton.

style : Permet de personnaliser l'apparence du bouton, comme la couleur de fond, la forme du


bouton, la taille, la couleur du texte, et d'autres propriétés visuelles.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple ElevatedButton'),

),

body: Center(

child: ElevatedButton(

onPressed: () {

// Action à effectuer lors du clic sur le bouton

print('Bouton pressé!');

},

child: Text('Cliquez ici'), // Texte à afficher sur le bouton

style: [Link](

primary: [Link], // Couleur de fond

onPrimary: [Link], // Couleur du texte

padding: [Link](horizontal: 30, vertical: 15), // Padding autour du texte

shape: RoundedRectangleBorder( // Forme du bouton

borderRadius: [Link](10),

), ), ), ), ), ) ; } }

21. IconButton
📌 Intérêt : Bouton avec une icône.

🔹 Propriétés : icon, onPressed

icon : Définit l'icône qui sera affichée sur le bouton. Vous pouvez utiliser des icônes pré-définies avec
Icons ou vos propres icônes.

onPressed : Cette propriété définit une fonction qui est appelée lorsque le bouton est pressé. Cela
représente l'action à effectuer lorsque l'utilisateur clique sur le bouton.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(

title: Text('Exemple IconButton'),

),

body: Center(

child: IconButton(

icon: Icon([Link]), // Icône à afficher (ici, une maison)

onPressed: () {

// Action à effectuer lors du clic sur le bouton

print('Icône cliquée!');

},

iconSize: 50, // Taille de l'icône

color: [Link], // Couleur de l'icône

), ), ), ) ; } }

Gestion des États et Asynchronisme

Widgets pour gérer le changement d’état et les données asynchrones.

22. StatefulWidget

📌 Intérêt : Crée un widget interactif avec un état modifiable.

23. StreamBuilder

📌 Intérêt : Affiche des données en temps réel.

🔹 Propriétés : stream, builder


stream : Le flux de données que le widget écoute. Cela peut être un Stream de données en continu
comme des événements ou des résultats d'une base de données.

builder : Une fonction qui permet de reconstruire l'interface utilisateur chaque fois que de nouvelles
données arrivent. Elle prend un contexte et un snapshot de données (qui représente l'état actuel du
flux) et permet de mettre à jour l'UI en fonction de l'état des données.

import 'dart:async';

import 'package:flutter/[Link]';

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

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('Exemple StreamBuilder')),

body: StreamExample(),

), ) ; } }

class StreamExample extends StatelessWidget {

// Création d'un Stream qui émet des nombres à intervalle régulier

Stream<int> numberStream() async* {

int i = 1;

while (true) {

await [Link](Duration(seconds: 1));

yield i++;

@override

Widget build(BuildContext context) {

return Center(

child: StreamBuilder<int>(

stream: numberStream(), // Stream qui émet des nombres

builder: (context, snapshot) {

// Vérification de l'état des données


if ([Link] == [Link]) {

return CircularProgressIndicator(); // Affiche une barre de progression pendant le chargement

} else if ([Link]) {

return Text('Erreur: ${[Link]}'); // Gère l'erreur si il y en a

} else if (![Link]) {

return Text('Aucune donnée'); // Si pas de données disponibles

} else {

return Text('Valeur actuelle: ${[Link]}'); // Affiche la donnée actuelle du flux

} }, ), ) ; } }

24. FutureBuilder

📌 Intérêt : Affiche un résultat asynchrone en attent un seul message.

🔹 Propriétés : future, builder

future : Il s'agit du Future qui représente l'opération asynchrone. Il renvoie une valeur ou une erreur
une fois l'opération terminée.

builder : Fonction qui permet de reconstruire l'interface utilisateur en fonction de l'état du Future.
Elle prend un contexte et un snapshot qui contient des informations sur l'état du Future.

import 'dart:async';

import 'package:flutter/[Link]';

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

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('Exemple FutureBuilder')),

body: FutureExample(),

), ) ; } }

class FutureExample extends StatelessWidget {

// Simulation d'une opération asynchrone qui retourne un Future

Future<String> fetchData() async {

await [Link](Duration(seconds: 3)); // Simule un délai de 3 secondes


return 'Données récupérées !';

@override

Widget build(BuildContext context) {

return Center(

child: FutureBuilder<String>(

future: fetchData(), // Le Future à attendre

builder: (context, snapshot) {

// Vérification de l'état du Future

if ([Link] == [Link]) {

return CircularProgressIndicator(); // Affiche un indicateur de chargement pendant l'attente

} else if ([Link]) {

return Text('Erreur: ${[Link]}'); // Affiche une erreur si le Future échoue

} else if (![Link]) {

return Text('Aucune donnée'); // Si le Future ne renvoie pas de données

} else {

return Text('Résultat : ${[Link]}'); // Affiche les données récupérées

} }, ), ) ; } }

25. Provider → Gestion d’état avec Provider

ChangeNotifier, Consumer, [Link]<T>()

Provider permet de gérer l'état dans une application Flutter de manière réactive et centralisée.

ChangeNotifier : Permet à un objet de notifier les autres widgets lorsqu'il y a un changement d'état.

Consumer : Écoute les modifications d'état et reconstruit l'UI.

[Link]<T>() : Permet de récupérer et de modifier l'état géré par le Provider.

import 'package:flutter/[Link]';

import 'package:provider/[Link]';

// ChangeNotifier pour gérer l'état

class Counter with ChangeNotifier {

int _count = 0;

int get count => _count;


void increment() {

_count++;

notifyListeners(); // Notifie les consommateurs lorsque l'état change

void main() {

runApp(

// Enveloppe l'application avec le Provider

ChangeNotifierProvider(

create: (context) => Counter(),

child: MyApp(),

),

);

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('Gestion d\'État avec Provider')),

body: Center(

child: Column(

mainAxisAlignment: [Link],

children: <Widget>[

// Utilisation de Consumer pour écouter les changements de l'état

Consumer<Counter>(

builder: (context, counter, child) {

return Text(

'Compteur: ${[Link]}',

style: TextStyle(fontSize: 32),

);
},

),

SizedBox(height: 20),

ElevatedButton(

onPressed: () {

// Utilisation de [Link] pour accéder à l'état et modifier les données

[Link]<Counter>(context, listen: false).increment();

},

child: Text('Incrémenter'),

), ], ), ), ), ) ; } }

Animation et Effets Visuels

Ajoute des animations à l’UI.

25. AnimatedContainer

📌 Intérêt : container animé , il Anime la taille, couleur, bordure, il st utile pour créer des animations
de transition..

🔹 Propriétés : duration, curve, width, height, color ,child , decoration ,

duration : Spécifie la durée de l'animation. Par exemple, Duration(seconds: 1) pour une animation qui
dure 1 seconde.

curve : Détermine l'effet de la courbe d'animation (ex. : linéaire, accéléré, etc.).

width et height : Définissent la largeur et la hauteur du container pendant l'animation.

color : Permet de changer la couleur de fond du AnimatedContainer.

child : L'enfant du container, un widget qui sera contenu dans le AnimatedContainer.

decoration : Utilisé pour ajouter une bordure, une ombre, ou un rayon de bordure, ce qui permet de
personnaliser l'apparence du container.

class MyApp extends StatefulWidget {

@override

_MyAppState createState() => _MyAppState();

}
class _MyAppState extends State<MyApp> {

double _width = 200.0;

double _height = 200.0;

Color _color = [Link];

// Animation du container

void _animateContainer() {

setState(() {

_width = _width == 200.0 ? 300.0 : 200.0;

_height = _height == 200.0 ? 300.0 : 200.0;

_color = _color == [Link] ? [Link] : [Link];

});

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('AnimatedContainer Example')),

body: Center(

child: AnimatedContainer(

duration: Duration(seconds: 1), // Durée de l'animation

curve: [Link], // Courbe d'animation

width: _width, // Largeur du container

height: _height, // Hauteur du container

color: _color, // Couleur du container

child: Center(child: Text('Hello!')), // Enfant du container

decoration: BoxDecoration(

borderRadius: [Link](15), // Rayon de bordure

),

// Lorsqu'on clique sur le container, on anime ses propriétés

onEnd: _animateContainer,
),

),

floatingActionButton: FloatingActionButton(

onPressed: _animateContainer, // Lance l'animation

child: Icon(Icons.play_arrow),

), ), ) ; } }

28. Opacity

📌 Intérêt : Permet de modifier l'opacité d'un widget.

🔹 Propriétés : opacity, child.

opacity : La valeur de l'opacité, un nombre entre 0.0 et 1.0. Une valeur de 0.0 signifie totalement
transparent, tandis que 1.0 signifie totalement opaque.

child : Le widget à affecter par l'opacité. Ce widget sera rendu avec le niveau de transparence
spécifié.

class MyApp extends StatefulWidget {

@override

_MyAppState createState() => _MyAppState();

class _MyAppState extends State<MyApp> {

double _opacity = 1.0;

// Change l'opacité du widget

void _changeOpacity() {

setState(() {

_opacity = _opacity == 1.0 ? 0.3 : 1.0; // Alterne entre opacité totale et partielle

});

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('Opacity Example')),

body: Center(
child: Opacity(

opacity: _opacity, // Définit l'opacité du widget

child: Container(

width: 200,

height: 200,

color: [Link],

child: Center(

child: Text(

'Opacity Change',

style: TextStyle(color: [Link], fontSize: 20),

), ), ), ), ),

floatingActionButton: FloatingActionButton(

onPressed: _changeOpacity, // Change l'opacité quand le bouton est pressé

child: Icon([Link]),

), ), ) ; } }

30. AnimatedOpacity

📌 Intérêt : Permet d’animer l’opacité d’un widget.

🔹 Propriétés : opacity, duration, curve.

opacity : La valeur de l’opacité, un nombre compris entre 0.0 (totalement transparent) et 1.0
(totalement opaque). Cette valeur sera progressivement atteinte grâce à l'animation.

duration : La durée de l'animation (la transition de l'opacité). Elle est définie en Duration (par
exemple, Duration(seconds: 1) pour une animation d'une seconde).

curve : La courbe d'animation qui définit le type de transition (par exemple, [Link],
[Link], etc.). Cela détermine comment l'animation s'accélère ou ralentit au fil du temps.

class MyApp extends StatefulWidget {

@override

_MyAppState createState() => _MyAppState();

class _MyAppState extends State<MyApp> {

double _opacity = 1.0;

// Change l'opacité avec une animation


void _changeOpacity() {

setState(() {

_opacity = _opacity == 1.0 ? 0.0 : 1.0; // Alterne entre opacité totale et invisible

});

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('AnimatedOpacity Example')),

body: Center(

child: AnimatedOpacity(

opacity: _opacity, // Définit l'opacité animée

duration: Duration(seconds: 1), // Durée de l'animation

curve: [Link], // Courbe d'animation (accélère puis ralentit)

child: Container(

width: 200,

height: 200,

color: [Link],

child: Center(

child: Text(

'Animated Opacity',

style: TextStyle(color: [Link], fontSize: 20),

), ), ), ), ),

floatingActionButton: FloatingActionButton(

onPressed: _changeOpacity, // Change l'opacité lors du clic sur le bouton

child: Icon([Link]),

), ), ) ; } }

26. Hero

📌 Intérêt : Crée une animation fluide entre deux é[Link] veut dire entre les routes

🔹 Propriétés : tag, child


tag : Un identifiant unique qui permet à Flutter de lier deux éléments entre les différentes routes. Ce
tag doit être identique dans les deux écrans où l’animation doit se produire.

child : Le widget à animer, comme une image ou un texte. Ce widget est celui qui sera animé d'un
écran à l'autre.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

routes: {

'/': (context) => FirstScreen(),

'/second': (context) => SecondScreen(),

},

initialRoute: '/',

);

class FirstScreen extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(title: Text('First Screen')),

body: Center(

child: Hero(

tag: 'hero-tag', // Le même tag sera utilisé dans le deuxième écran

child: Material(

color: [Link],

child: InkWell(

onTap: () {

[Link](context, '/second'); // Navigation vers le second écran

},

child: Container(

width: 200,
height: 200,

color: [Link],

child: Center(

child: Text(

'Tap me!',

style: TextStyle(color: [Link], fontSize: 20),

), ), ), ), ), ), ), ) ; } }

class SecondScreen extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(title: Text('Second Screen')),

body: Center(

child: Hero(

tag: 'hero-tag', // Le même tag que dans le premier écran

child: Material(

color: [Link],

child: Container(

width: 300, // Augmenter la taille pour l'animation

height: 300,

color: [Link],

child: Center(

child: Text(

'Hello from second screen!',

style: TextStyle(color: [Link], fontSize: 20),

),),),),),),) ;}}

Navigation et Gestion d’Écrans

Gère le passage d’un écran à un autre.

Navigator

📌 Intérêt : Permet de naviguer entre les écrans.


🔹 Méthodes principales : push(), pop(), pushReplacement()

push() : Ajoute un nouvel écran à la pile de navigation. Cela signifie qu'un nouvel écran est affiché
par-dessus l'écran actuel.

pop() : Retire l'écran actuel de la pile, ce qui renvoie l'utilisateur à l'écran précédent.

pushReplacement() : Remplace l'écran actuel par un autre, sans ajouter une nouvelle entrée dans la
pile. Cela permet de supprimer l'écran actuel et de le remplacer par un autre.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: FirstScreen(),

);

class FirstScreen extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(title: Text('First Screen')),

body: Center(

child: Column(

mainAxisAlignment: [Link],

children: [

ElevatedButton(

onPressed: () {

// Naviguer vers le second écran en utilisant push

[Link](

context,

MaterialPageRoute(builder: (context) => SecondScreen()),

);

},

child: Text('Go to Second Screen'),


),

ElevatedButton(

onPressed: () {

// Remplacer l'écran actuel par un autre écran

[Link](

context,

MaterialPageRoute(builder: (context) => ThirdScreen()),

);

},

child: Text('Replace with Third Screen'),

), ], ), ), ) ; } }

class SecondScreen extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(title: Text('Second Screen')),

body: Center(

child: ElevatedButton(

onPressed: () {

// Retirer l'écran actuel et revenir au premier écran

[Link](context);

},

child: Text('Back to First Screen'),

), ), ) ; } }

class ThirdScreen extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(title: Text('Third Screen')),

body: Center(

child: ElevatedButton(
onPressed: () {

// Retirer l'écran actuel et revenir au premier écran

[Link](context);

},

child: Text('Back to First Screen'),

), ), ) ; } }

PageView

📌 Intérêt : Affiche plusieurs pages en mode glissement.

🔹 Propriétés : children, controller, scrollDirection

children : Liste des widgets à afficher dans le PageView. Ce sont les pages ou vues que l'utilisateur
peut faire défiler.

controller : Un objet PageController utilisé pour contrôler la position de la page, la navigation, et la


vitesse de défilement.

scrollDirection : Définit la direction du défilement. Par défaut, il est horizontal, mais peut être changé
pour vertical en modifiant cette propriété.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: MyPageView(),

);

class MyPageView extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(title: Text('PageView Example')),

body: PageView(

// Contrôler la navigation entre les pages avec un PageController


controller: PageController(),

scrollDirection: [Link], // Défilement horizontal

children: <Widget>[

Container(

color: [Link],

child: Center(child: Text('Page 1', style: TextStyle(fontSize: 24, color: [Link]))),

),

Container(

color: [Link],

child: Center(child: Text('Page 2', style: TextStyle(fontSize: 24, color: [Link]))),

),

Container(

color: [Link],

child: Center(child: Text('Page 3', style: TextStyle(fontSize: 24, color: [Link]))),

), ], ), ) ; } }

Médias et Interactions

Widgets pour gérer des images, vidéos, etc.

Image

📌 Intérêt : Affiche une image locale ou en ligne.

🔹 Propriétés : image, fit, height, width

image : L'image à afficher. Elle peut être une image locale (fichier) ou une image en ligne (via une
URL).

fit : Détermine comment l'image doit être ajustée dans son espace. Par exemple, elle peut être
redimensionnée pour remplir l'espace disponible ou pour conserver ses proportions.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('Image Example')),

body: Column(
children: [

// Image locale

[Link]('assets/local_image.jpg', height: 200, width: 200, fit: [Link]),

// Image en ligne

[Link]('[Link] height: 200, width: 200, fit: [Link]),

], ), ), ) ; } }

GestureDetector

📌 Intérêt : Capture les gestes de l’utilisateur (tap, swipe, etc.).

🔹 Propriétés : onTap, onLongPress, onPanUpdate

onTap : Définit l'action à exécuter lorsque l'utilisateur tape (touche rapidement) sur le widget.

onLongPress : Définit l'action à exécuter lorsqu'un appui long est effectué sur le widget.

onPanUpdate : Détecte un mouvement de glissement (pan) et fournit des informations sur le


déplacement de l'utilisateur.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('GestureDetector Example')),

body: Center(

child: GestureDetector(

onTap: () {

print('Tap detected!');

},

onLongPress: () {

print('Long press detected!');

},

onPanUpdate: (details) {

print('Pan detected: ${[Link]}');

},

child: Container(
color: [Link],

width: 200,

height: 200,

child: Center(child: Text('Tap or Long Press')),

), ), ), ), ) ; } }

Formulaires et Validation des Données

🔹 Pour gérer les entrées utilisateur et leur validation.

Form → Conteneur pour champs de texte

child, key

Le Form permet de regrouper des champs de formulaire dans un widget avec un état.

La clé permet de valider le formulaire, récupérer les données, ou réinitialiser l'état des champs.

Utilisé pour gérer les entrées d'utilisateur, avec des mécanismes de validation et de soumission des
données.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('Form Example')),

body: Padding(

padding: const [Link](16.0),

child: MyForm(),

), ), ) ; } }

class MyForm extends StatefulWidget {

@override

_MyFormState createState() => _MyFormState();

class _MyFormState extends State<MyForm> {

// Déclaration d'une clé globale pour le formulaire

final _formKey = GlobalKey<FormState>();


// Contrôleur pour le champ de texte

final _controller = TextEditingController();

@override

Widget build(BuildContext context) {

return Form(

key: _formKey, // Utilisation de la clé pour identifier ce formulaire

child: Column(

children: <Widget>[

TextFormField(

controller: _controller,

decoration: InputDecoration(labelText: 'Votre nom'),

validator: (value) {

if (value == null || [Link]) {

return 'Veuillez entrer votre nom';

return null;

},

),

ElevatedButton(

onPressed: () {

if (_formKey.currentState!.validate()) {

// Si le formulaire est valide, affiche un message

[Link](context).showSnackBar(SnackBar(content: Text('Formulaire valide')));

},

child: Text('Soumettre'),

), ], ), ) ; } }

28. TextFormField → Champ de saisie avancé

validator, keyboardType, obscureText


validator : Fonction utilisée pour valider l'entrée du champ de texte. Elle prend une valeur en
paramètre et renvoie un message d'erreur si la validation échoue.

keyboardType : Détermine le type de clavier affiché, par exemple [Link] pour


un champ de saisie d'email.

obscureText : Si true, le texte est masqué (utilisé pour les mots de passe ou toute autre donnée
sensible).

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text('TextFormField Example')),

body: Padding(

padding: const [Link](16.0),

child: MyForm(),

), ), ) ; } }

class MyForm extends StatefulWidget {

@override

_MyFormState createState() => _MyFormState();

class _MyFormState extends State<MyForm> {

final _formKey = GlobalKey<FormState>(); // Clé globale pour le formulaire

final _emailController = TextEditingController();

final _passwordController = TextEditingController();

@override

Widget build(BuildContext context) {

return Form(

key: _formKey, // Liée au formulaire

child: Column(

children: <Widget>[

TextFormField(

controller: _emailController,
decoration: InputDecoration(labelText: 'Email'),

keyboardType: [Link], // Clavier pour email

validator: (value) {

if (value == null || [Link]) {

return 'Veuillez entrer votre email';

} else if (!RegExp(r'^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$').hasMatch(value)) {

return 'Entrez un email valide';

return null;

},

),

TextFormField(

controller: _passwordController,

decoration: InputDecoration(labelText: 'Mot de passe'),

obscureText: true, // Cache le texte (utile pour le mot de passe)

validator: (value) {

if (value == null || [Link]) {

return 'Veuillez entrer un mot de passe';

} else if ([Link] < 6) {

return 'Le mot de passe doit contenir au moins 6 caractères';

return null;

},

),

ElevatedButton(

onPressed: () {

if (_formKey.currentState!.validate()) {

// Si le formulaire est valide

[Link](context).showSnackBar(SnackBar(content: Text('Formulaire soumis')));

},
child: Text('Soumettre'),

), ], ), ) ; } }

Le TextFormField permet de créer des champs de saisie de texte avec des fonctionnalités avancées
comme la validation, l'affichage d'un clavier spécifique, et la possibilité de masquer le texte.

Il est souvent utilisé dans des Form pour gérer plusieurs champs de saisie à la fois, et pour s'assurer
que les données saisies respectent certaines règles avant d'être soumises.

Widgets Spécifiques aux Applications Modernes

🔹 Pour ajouter des fonctionnalités avancées.

29. SliverAppBar → Barre d’application extensible

expandedHeight, flexibleSpace

expandedHeight : Définit la hauteur maximale de la barre d'application lorsque l'utilisateur ne fait pas
défiler l'écran.

flexibleSpace : Permet de personnaliser l'espace flexible qui sera utilisé à l'intérieur de la barre
d'application. Par exemple, vous pouvez y ajouter une image d'arrière-plan qui se réduit ou se
déplace lorsqu'on fait défiler la page.

collapsedHeight : Hauteur de la barre d'application lorsque la page est complètement défilée.

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: SliverAppBarExample(),

);

class SliverAppBarExample extends StatelessWidget {

@override

Widget build(BuildContext context) {

return Scaffold(

body: CustomScrollView(

slivers: <Widget>[

SliverAppBar(

expandedHeight: 200.0, // Hauteur maximale


floating: false, // Pas de barre flottante

pinned: true, // Reste affichée en haut de l'écran même quand on défile

flexibleSpace: FlexibleSpaceBar(

title: Text('SliverAppBar Example'), // Titre qui reste visible

background: [Link](

'[Link]

fit: [Link], // Image d'arrière-plan

),

),

),

SliverList(

delegate: SliverChildBuilderDelegate(

(BuildContext context, int index) {

return ListTile(

title: Text('Item #$index'),

);

},

childCount: 50, // Nombre d'éléments de la liste

), ), ], ), ) ; } }

Le SliverAppBar est un widget très puissant pour gérer des barres d'applications extensibles avec des
animations liées au défilement. Il permet de créer une interface fluide et visuellement attractive,
idéale pour les applications où l'on veut un AppBar dynamique et flexible.

30. Dismissible → Swipe pour supprimer un élément

key, background, onDismissed

key : Une clé unique pour le widget Dismissible. Cela permet à Flutter de maintenir l'état du widget
lorsqu'il est redessiné.

background : Ce widget est affiché lorsqu'un élément est glissé. Par exemple, vous pouvez y afficher
une couleur de fond ou une icône pour indiquer l'action à effectuer (comme la suppression).

onDismissed : C'est la fonction qui est appelée lorsque l'utilisateur fait glisser et supprime l'élément.
Cette fonction vous permet de mettre à jour la source de données et d'effectuer toute autre action
après la suppression.
class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: DismissibleExample(),

);

class DismissibleExample extends StatelessWidget {

// Liste d'exemple d'éléments

final List<String> items = [Link](20, (index) => 'Item #$index');

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(

title: Text('Dismissible Example'),

),

body: [Link](

itemCount: [Link],

itemBuilder: (context, index) {

return Dismissible(

key: Key(items[index]), // Clé unique pour chaque item

onDismissed: (direction) {

// Action après suppression

[Link](context).showSnackBar(

SnackBar(content: Text('${items[index]} dismissed')),

);

// Supprimer l'élément de la liste

[Link](index);

},
background: Container(

color: [Link], // Couleur de fond quand l'élément est glissé

child: Align(

alignment: [Link],

child: Padding(

padding: const [Link](16.0),

child: Icon([Link], color: [Link]),

),

),

),

child: ListTile(

title: Text(items[index]), // Affichage de l'élément de la liste

), ) ; } , ), ) ; } }

Le Dismissible est un widget très pratique pour ajouter une fonctionnalité de suppression d'éléments
via un geste de balayage. Il est utile dans les interfaces où l'utilisateur veut pouvoir supprimer
rapidement des éléments dans des listes ou des listes de tâches.

Gestion de la Base de Données et API (Backend)

🔹 Pour récupérer et stocker des données dans une base de données.

31. Firebase (Cloud Firestore, Auth, Storage)

FirebaseAuth, FirebaseFirestore, FirebaseStorage

FirebaseAuth (Gestion des utilisateurs) :

Permet d'authentifier les utilisateurs via des méthodes telles que l'email et le mot de passe, les
comptes Google, Facebook, et d'autres fournisseurs d'authentification tiers.

Permet de gérer l'inscription, la connexion et la déconnexion des utilisateurs.

Propriétés principales :

createUserWithEmailAndPassword() : Créer un utilisateur avec email et mot de passe.

signInWithEmailAndPassword() : Authentification avec email et mot de passe.

signInWithCredential() : Authentification via des fournisseurs externes.

signOut() : Déconnexion de l'utilisateur.


FirebaseFirestore (Base de données en temps réel) :

Base de données NoSQL qui permet de stocker et de récupérer des données en temps réel.

Elle est conçue pour évoluer avec des applications mobiles ou web à grande échelle.

Permet de stocker des documents sous forme de collections.

Propriétés principales :

collection() : Accède à une collection spécifique.

doc() : Accède à un document spécifique d’une collection.

add() : Ajouter un document à une collection.

get() : Récupérer les données d'un document ou d'une collection.

update() : Met à jour les données d'un document.

FirebaseStorage (Stockage de fichiers) :

Permet de stocker des fichiers (images, vidéos, audios, etc.) dans le cloud.

Le stockage est optimisé pour les fichiers volumineux et peut être utilisé pour gérer le contenu
multimédia dans votre application.

Propriétés principales :

ref() : Accéder à un fichier dans le stockage.

putFile() : Charger un fichier dans le stockage.

getDownloadURL() : Récupérer l'URL d'un fichier stocké.

delete() : Supprimer un fichier du stockage.

import 'package:firebase_auth/firebase_auth.dart';

import 'package:cloud_firestore/cloud_firestore.dart';

import 'package:firebase_storage/firebase_storage.dart';

import 'package:flutter/[Link]';

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

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {


return MaterialApp(

home: FirebaseExample(),

);

class FirebaseExample extends StatefulWidget {

@override

_FirebaseExampleState createState() => _FirebaseExampleState();

class _FirebaseExampleState extends State<FirebaseExample> {

final FirebaseAuth _auth = [Link];

final FirebaseFirestore _firestore = [Link];

final FirebaseStorage _storage = [Link];

User? _user;

// Méthode d'inscription

Future<void> _signUp() async {

try {

UserCredential userCredential = await _auth.createUserWithEmailAndPassword(

email: "test@[Link]",

password: "password123",

);

setState(() {

_user = [Link];

});

} catch (e) {

print("Erreur d'inscription: $e");

// Méthode d'ajout de données à Firestore

Future<void> _addData() async {

await _firestore.collection('users').add({
'name': 'John Doe',

'email': 'test@[Link]',

'createdAt': [Link](),

});

// Méthode de téléchargement de fichier vers Firebase Storage

Future<void> _uploadFile() async {

try {

final ref = _storage.ref().child('images/[Link]');

await [Link](await _getSampleFile());

String downloadURL = await [Link]();

print("URL du fichier téléchargé: $downloadURL");

} catch (e) {

print("Erreur de téléchargement: $e");

// Simule la récupération d'un fichier

Future<File> _getSampleFile() async {

// Ici, vous pourriez récupérer un fichier depuis la galerie ou la caméra

// Exemple simple d'un fichier temporaire

return File('path_to_sample_image.jpg');

@override

Widget build(BuildContext context) {

return Scaffold(

appBar: AppBar(title: Text("Firebase Example")),

body: Column(

children: [

ElevatedButton(

onPressed: _signUp,

child: Text('S\'inscrire'),
),

ElevatedButton(

onPressed: _addData,

child: Text('Ajouter des données à Firestore'),

),

ElevatedButton(

onPressed: _uploadFile,

child: Text('Télécharger un fichier'),

),

_user != null

? Text("Utilisateur connecté: ${_user?.email}")

: Text("Aucun utilisateur connecté"),

], ), ) ; } }

32. Http (Appels API REST)

[Link](), [Link](), [Link](), [Link]()

[Link]()

Permet de faire une requête GET pour récupérer des données depuis une API.

Utilisé pour obtenir des informations depuis un serveur ou une base de données.

Exemple : Récupérer des informations utilisateur depuis une API.

import 'package:http/[Link]' as http;

Future<void> fetchData() async {

final response = await [Link]([Link]('[Link]

if ([Link] == 200) {

// Si la requête est réussie, traiter les données ici.

print([Link]);

} else {

// Si la requête échoue, gérer l'erreur.

print('Erreur de récupération des données');

}
}

[Link]()

Permet de faire une requête POST pour envoyer des données à un serveur.

Utilisé pour créer de nouvelles ressources ou soumettre des informations à un serveur.

Exemple : Créer un nouvel utilisateur en envoyant des informations via POST.

Future<void> createUser(String name, String email) async {

final response = await [Link](

[Link]('[Link]

headers: {"Content-Type": "application/json"},

body: '{"name": "$name", "email": "$email"}',

);

if ([Link] == 201) {

// Si la requête est réussie, gérer la réponse ici.

print('Utilisateur créé avec succès');

} else {

// Si la requête échoue, gérer l'erreur.

print('Erreur lors de la création de l\'utilisateur');

[Link]()

Permet de faire une requête PUT pour mettre à jour une ressource existante.

Utilisé pour mettre à jour des informations sur une ressource sur le serveur.

Exemple : Mettre à jour un utilisateur existant.

Future<void> updateUser(int id, String name, String email) async {

final response = await [Link](

[Link]('[Link]

headers: {"Content-Type": "application/json"},


body: '{"name": "$name", "email": "$email"}',

);

if ([Link] == 200) {

// Si la requête est réussie, gérer la réponse ici.

print('Utilisateur mis à jour');

} else {

// Si la requête échoue, gérer l'erreur.

print('Erreur lors de la mise à jour de l\'utilisateur');

[Link]()

Permet de faire une requête DELETE pour supprimer une ressource.

Utilisé pour supprimer une ressource (comme un utilisateur) sur le serveur.

Exemple : Supprimer un utilisateur.

Future<void> deleteUser(int id) async {

final response = await [Link](

[Link]('[Link]

);

if ([Link] == 200) {

// Si la requête est réussie, gérer la réponse ici.

print('Utilisateur supprimé');

} else {

// Si la requête échoue, gérer l'erreur.

print('Erreur lors de la suppression de l\'utilisateur');

Exemple de flux complet (CRUD) avec http :


import 'package:http/[Link]' as http;

import 'dart:convert';

Future<void> main() async {

// Récupérer des données

await fetchData();

// Créer un utilisateur

await createUser('John Doe', '[Link]@[Link]');

// Mettre à jour un utilisateur

await updateUser(1, 'John Doe', '[Link]@[Link]');

// Supprimer un utilisateur

await deleteUser(1);

Future<void> fetchData() async {

final response = await [Link]([Link]('[Link]

if ([Link] == 200) {

// Traitement des données récupérées

print(jsonDecode([Link]));

} else {

print('Erreur de récupération des données');

Future<void> createUser(String name, String email) async {

final response = await [Link](

[Link]('[Link]

headers: {"Content-Type": "application/json"},

body: jsonEncode({"name": name, "email": email}),

);

if ([Link] == 201) {

print('Utilisateur créé avec succès');

} else {

print('Erreur lors de la création de l\'utilisateur');


}

Future<void> updateUser(int id, String name, String email) async {

final response = await [Link](

[Link]('[Link]

headers: {"Content-Type": "application/json"},

body: jsonEncode({"name": name, "email": email}),

);

if ([Link] == 200) {

print('Utilisateur mis à jour');

} else {

print('Erreur lors de la mise à jour de l\'utilisateur');

Future<void> deleteUser(int id) async {

final response = await [Link]([Link]('[Link]

if ([Link] == 200) {

print('Utilisateur supprimé');

} else {

print('Erreur lors de la suppression de l\'utilisateur');

La bibliothèque http permet de gérer facilement les appels API REST dans vos applications Flutter

*************************************************************************

33. SharedPreferences → Stockage local simple

setString(), getString(), setBool(), getBool()

setString()

Permet de stocker une valeur de type String dans les préférences locales.

Exemple : Stocker le nom de l'utilisateur.


import 'package:shared_preferences/shared_preferences.dart';

Future<void> saveName(String name) async {

SharedPreferences prefs = await [Link]();

await [Link]('userName', name);

getString()

Permet de récupérer une valeur de type String à partir des préférences locales.

Exemple : Récupérer le nom de l'utilisateur.

Future<String?> getName() async {

SharedPreferences prefs = await [Link]();

return [Link]('userName');

setBool()

Permet de stocker une valeur de type bool dans les préférences locales.

Exemple : Stocker si l'utilisateur est connecté ou non.

Future<void> saveLoginStatus(bool isLoggedIn) async {

SharedPreferences prefs = await [Link]();

await [Link]('isLoggedIn', isLoggedIn);

getBool()

Permet de récupérer une valeur de type bool à partir des préférences locales.

Exemple : Récupérer l'état de connexion de l'utilisateur.

Future<bool> getLoginStatus() async {

SharedPreferences prefs = await [Link]();

return [Link]('isLoggedIn') ?? false; // Valeur par défaut false

Code complet :

import 'package:shared_preferences/shared_preferences.dart';

Future<void> main() async {


// Sauvegarder les données

await saveName('John Doe');

await saveLoginStatus(true);

// Récupérer les données

String? name = await getName();

bool isLoggedIn = await getLoginStatus();

// Afficher les données

print('Nom: $name');

print('Est connecté: $isLoggedIn');

// Sauvegarder un nom

Future<void> saveName(String name) async {

SharedPreferences prefs = await [Link]();

await [Link]('userName', name);

// Récupérer un nom

Future<String?> getName() async {

SharedPreferences prefs = await [Link]();

return [Link]('userName');

// Sauvegarder l'état de connexion

Future<void> saveLoginStatus(bool isLoggedIn) async {

SharedPreferences prefs = await [Link]();

await [Link]('isLoggedIn', isLoggedIn);

// Récupérer l'état de connexion

Future<bool> getLoginStatus() async {

SharedPreferences prefs = await [Link]();

return [Link]('isLoggedIn') ?? false; // Valeur par défaut false

Avantages de l'utilisation de SharedPreferences :


Simple à utiliser pour stocker des données simples, comme des préférences de l'utilisateur.

Idéal pour les configurations de l'application ou le stockage des paramètres, comme le nom
d'utilisateur, les préférences d'interface, ou l'état de la connexion.

Il est persistant entre les sessions de l'application, c'est-à-dire que les données restent intactes
même si l'application est fermée et redémarrée.

Remarque :

SharedPreferences est principalement destiné à de petites quantités de données. Si vous avez besoin
de stocker des données plus volumineuses ou complexes, une base de données comme SQLite ou
Firebase pourrait être plus appropriée.

34. SQFlite → Base de données locale SQLite

insert(), query(), update(), delete()

insert()

Permet d'insérer des données dans une table.

Exemple : Ajouter un nouvel utilisateur dans la table users.

++++++++++++++++++++++++++++++++++++

import 'package:sqflite/[Link]';

import 'package:path/[Link]';

// Insérer des données dans la table

Future<void> insertUser(Database db, Map<String, dynamic> user) async {

await [Link](

'users',

user,

conflictAlgorithm: [Link], // Remplacer en cas de conflit

);

query()

Permet de récupérer des données depuis une table.

Exemple : Récupérer tous les utilisateurs de la table users.

// Récupérer toutes les lignes de la table 'users'


Future<List<Map<String, dynamic>>> queryUsers(Database db) async {

return await [Link]('users');

update()

Permet de mettre à jour des données existantes dans une table.

Exemple : Mettre à jour les informations d'un utilisateur.

// Mettre à jour un utilisateur

Future<void> updateUser(Database db, int id, Map<String, dynamic> newUser) async {

await [Link](

'users',

newUser,

where: 'id = ?',

whereArgs: [id],

);

delete()

Permet de supprimer des données d'une table.

Exemple : Supprimer un utilisateur par son identifiant.

// Supprimer un utilisateur

Future<void> deleteUser(Database db, int id) async {

await [Link](

'users',

where: 'id = ?',

whereArgs: [id],

);

Code complet :

import 'package:sqflite/[Link]';

import 'package:path/[Link]';

class UserDatabase {
// Ouvrir la base de données

Future<Database> openDatabase() async {

String path = await getDatabasesPath();

return openDatabase(

join(path, 'user_database.db'),

onCreate: (db, version) async {

await [Link]('''

CREATE TABLE users(

id INTEGER PRIMARY KEY AUTOINCREMENT,

name TEXT,

age INTEGER

''');

},

version: 1,

);

// Insérer un utilisateur

Future<void> insertUser(Database db, Map<String, dynamic> user) async {

await [Link](

'users',

user,

conflictAlgorithm: [Link],

);

// Récupérer tous les utilisateurs

Future<List<Map<String, dynamic>>> queryUsers(Database db) async {

return await [Link]('users');

// Mettre à jour un utilisateur

Future<void> updateUser(Database db, int id, Map<String, dynamic> newUser) async {


await [Link](

'users',

newUser,

where: 'id = ?',

whereArgs: [id],

);

// Supprimer un utilisateur

Future<void> deleteUser(Database db, int id) async {

await [Link](

'users',

where: 'id = ?',

whereArgs: [id],

);

void main() async {

// Ouvrir la base de données

final userDb = UserDatabase();

Database db = await [Link]();

// Ajouter un utilisateur

await [Link](db, {'name': 'John Doe', 'age': 30});

// Récupérer les utilisateurs

List<Map<String, dynamic>> users = await [Link](db);

print('Users: $users');

// Mettre à jour un utilisateur

await [Link](db, 1, {'name': 'Jane Doe', 'age': 28});

// Supprimer un utilisateur

await [Link](db, 1);

}
Avantages de SQFlite :

Stockage local fiable : SQFlite permet de travailler avec une base de données SQLite locale, ce qui
est parfait pour les applications Flutter qui nécessitent un stockage structuré et performant.

Transactions : SQFlite supporte les transactions, ce qui permet de garantir que plusieurs requêtes
SQL sont exécutées de manière atomique.

Support des requêtes complexes : Vous pouvez exécuter des requêtes SQL complexes pour
interroger et manipuler vos données.

Remarque :

SQFlite est idéal pour les applications qui nécessitent de gérer une grande quantité de données
locales structurées de manière relationnelle. Toutefois, pour des données non structurées ou pour
une base de données en temps réel, d'autres solutions comme Firebase peuvent être préférables.

Gestion des Notifications et Permissions

🔹 Pour envoyer des notifications et demander des accès.

35. Flutter Local Notifications

show(), schedule()

show()

Permet d'afficher immédiatement une notification locale.

Exemple : Afficher une notification simple.

import 'package:flutter_local_notifications/flutter_local_notifications.dart';

FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin = FlutterLocalNotificationsPlugin();

Future<void> showNotification() async {

var androidDetails = AndroidNotificationDetails(

'your_channel_id',

'your_channel_name',

channelDescription: 'your_channel_description',

importance: [Link],

priority: [Link],

);

var platformDetails = NotificationDetails(android: androidDetails);


await [Link](

0, // ID de la notification

'Titre de la Notification', // Titre

'Contenu de la notification', // Contenu

platformDetails, // Détails de la plateforme (Android)

);

schedule()

Permet de planifier une notification pour qu'elle apparaisse à un moment spécifique dans le futur.

Exemple : Planifier une notification pour un rappel.

import 'package:flutter_local_notifications/flutter_local_notifications.dart';

Future<void> scheduleNotification() async {

var scheduledDate = [Link]().add(Duration(seconds: 10)); // Planifier 10 secondes après le


moment actuel.

var androidDetails = AndroidNotificationDetails(

'your_channel_id',

'your_channel_name',

channelDescription: 'your_channel_description',

importance: [Link],

priority: [Link],

);

var platformDetails = NotificationDetails(android: androidDetails);

await [Link](

0, // ID de la notification

'Rappel', // Titre de la notification

'Ceci est un rappel programmé.', // Contenu de la notification


scheduledDate, // Moment où la notification sera envoyée

platformDetails, // Détails pour chaque plateforme

androidAllowWhileIdle: true, // Permet de recevoir des notifications même lorsque l'appareil est
en veille

matchDateTimeComponents: [Link], // Planifier à un moment précis

);

Exemple complet d'intégration avec flutter_local_notifications :

Ajouter le package flutter_local_notifications à [Link] :

dependencies:

flutter:

sdk: flutter

flutter_local_notifications: ^12.0.0

Initialiser le plugin dans le [Link] :

import 'package:flutter/[Link]';

import 'package:flutter_local_notifications/flutter_local_notifications.dart';

void main() async {

[Link]();

FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin = FlutterLocalNotificationsPlugin();

var androidInitializationSettings = AndroidInitializationSettings('app_icon');

var initializationSettings = InitializationSettings(android: androidInitializationSettings);

await [Link](initializationSettings);

runApp(MyApp());

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(
home: Scaffold(

appBar: AppBar(title: Text("Notifications Flutter")),

body: Center(

child: ElevatedButton(

onPressed: () {

showNotification();

scheduleNotification();

},

child: Text("Envoyer Notification"),

), ), ), ) ; } }

Permission Handler

request(), checkPermissionStatus()

request()

Permet de demander une ou plusieurs permissions à l'utilisateur. Si la permission n'est pas encore
accordée, cette méthode déclenchera une fenêtre contextuelle pour que l'utilisateur puisse l'accepter
ou la refuser.

import 'package:permission_handler/permission_handler.dart';

Future<void> requestCameraPermission() async {

// Demande la permission d'accéder à la caméra

PermissionStatus status = await [Link]();

if ([Link]) {

print("Permission accordée pour la caméra !");

} else if ([Link]) {

print("Permission refusée pour la caméra.");

} else if ([Link]) {

// Si la permission est définitivement refusée, guide l'utilisateur pour la permettre via les
paramètres

openAppSettings();

checkPermissionStatus()
Vérifie l'état actuel d'une permission. Cela permet de savoir si la permission est accordée, refusée
ou si elle est encore en attente d'une action de l'utilisateur.

import 'package:permission_handler/permission_handler.dart';

Future<void> checkCameraPermission() async {

// Vérifie si la permission d'accéder à la caméra est déjà accordée

PermissionStatus status = await [Link];

if ([Link]) {

print("La caméra est accessible.");

} else if ([Link]) {

print("La permission pour la caméra est refusée.");

} else if ([Link]) {

print("La permission pour la caméra est définitivement refusée.");

Exemple complet d'intégration avec permission_handler :

Ajouter le package permission_handler dans [Link] :

dependencies:

permission_handler: ^10.2.0

Initialisation de l'application et demande de permission pour la caméra :

import 'package:flutter/[Link]';

import 'package:permission_handler/permission_handler.dart';

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

class MyApp extends StatelessWidget {

@override

Widget build(BuildContext context) {

return MaterialApp(

home: Scaffold(

appBar: AppBar(title: Text("Gestion des Permissions")),

body: Center(
child: ElevatedButton(

onPressed: () async {

// Demande la permission d'accéder à la caméra

await requestCameraPermission();

},

child: Text("Demander la permission de la caméra"),

), ), ), ) ; } }

// Demander la permission d'accéder à la caméra

Future<void> requestCameraPermission() async {

PermissionStatus status = await [Link]();

if ([Link]) {

print("Permission accordée pour la caméra !");

} else if ([Link]) {

print("Permission refusée pour la caméra.");

} else if ([Link]) {

// Ouvrir les paramètres si la permission est définitivement refusée

openAppSettings();

Avantages de permission_handler :

Gestion simplifiée des permissions : Permet de demander et vérifier les permissions de manière
fluide pour une variété de fonctionnalités (caméra, microphone, localisation, etc.).

Compatibilité multiplateforme : Fonctionne à la fois sur Android et iOS, avec un comportement


cohérent sur les deux plateformes.

Gestion des permissions permanentes : Si une permission est refusée de manière permanente,
vous pouvez guider l'utilisateur vers les paramètres de l'application pour la changer.

Sécurisé : Assure que l'application ne tente pas d'accéder à des fonctionnalités sensibles sans la
permission de l'utilisateur.

attention !!!!!!!!!!!!!

Avant d'utiliser permission_handler, vous devez vous assurer que vous avez correctement configuré
votre fichier [Link] pour Android et le fichier [Link] pour iOS, en fonction des
permissions que vous demandez. Par exemple, pour accéder à la caméra sur Android, vous devez
ajouter la permission suivante dans [Link] :
<uses-permission android:name="[Link]"/>

Et pour iOS, dans le fichier [Link], ajoutez :

<key>NSCameraUsageDescription</key>

<string>Nous avons besoin d'accéder à votre caméra</string>

Widgets Spécifiques pour les Apps Mobile Complètes

🔹 Pour enrichir ton application avec des fonctionnalités avancées.

37. Google Maps → Affichage de cartes

GoogleMap(), markers, initialCameraPosition

*************************************************************************

38. Geolocator → Géolocalisation

getCurrentPosition(), getPositionStream()

*************************************************************************

39. Camera → Accès à l’appareil photo

initialize(), takePicture()

*************************************************************************

40. VideoPlayer → Lecture de vidéos

controller, initialize(), play(), pause()

Sécurité et Authentification

🔹 Gestion des utilisateurs et protection des données.

Firebase Authentication → Connexion avec Google, Facebook, Email/Password

*************************************************************************

JWT (JSON Web Tokens) → Authentification sécurisée avec API


*************************************************************************

Biometric Authentication → Empreintes digitales, reconnaissance faciale

*************************************************************************

Encryption → Chiffrement des données sensibles

Performance et Optimisation

🔹 Améliorer la fluidité et la rapidité de l’app.

Isolates → Exécuter des tâches lourdes en arrière-plan

*************************************************************************

Code Splitting → Séparer le code en modules pour optimiser le chargement

*************************************************************************

Caching (Hive, SharedPreferences) → Stockage rapide des données

Accessibilité et UI Responsive

🔹 Adapter l’UI pour tous les types d’écrans et d’utilisateurs.

MediaQuery → Adapter la mise en page à la taille de l’écran

*************************************************************************

Accessibility (Semantics, VoiceOver) → Améliorer l’accessibilité pour tous

*************************************************************************

ResponsiveBuilder → Gestion des tailles d’écran

Tests et Déploiement

🔹 Garantir la qualité et la stabilité de l’application.

Unit Tests (flutter_test) → Tester chaque fonction

*************************************************************************

Widget Tests → Tester les interactions utilisateur

*************************************************************************
Integration Tests → Tester l’ensemble de l’application

*************************************************************************

CI/CD (Codemagic, GitHub Actions) → Automatiser les tests et le déploiement

Intégration avec le Hardware et IoT

🔹 Ajouter des fonctionnalités liées aux capteurs et périphériques.

Bluetooth (flutter_blue) → Connexion à des appareils Bluetooth

*************************************************************************

NFC (Near Field Communication) → Lire/écrire des cartes NFC

*************************************************************************

Sensors (accelerometer, gyroscope) → Utiliser les capteurs du téléphone

Vous aimerez peut-être aussi