• Contenu
  • Bas de page
blog-ouidou_logoblog-ouidou_logoblog-ouidou_logoblog-ouidou_logo
  • Actualités Ouidou
  • Articles Techniques
  • Livres blancs
  • Interviews Clients
  • Interviews collaborateurs
Découvrir Ouidou
✕
No results See all results
Les e-mails c’est bien, mangez-en !

Les e-mails c’est bien, mangez-en !

13 février 2020
Qui impliquer dans la rédaction du cahier des charges de votre application ?

Qui impliquer dans la rédaction du cahier des charges de votre application ?

24 mars 2020
Ressources > Découverte d’un composant Flutter

Découverte d’un composant Flutter

Article écrit par Victor Darras

Aujourd’hui, nous allons parler un peu de développement mobile. Récemment chez Ouidou nous avons pris du temps pour essayer un nouvel environnement de travail composé de Dart, un langage statiquement typé, orienté objet avec une syntaxe relativement proche de JavaScript ; et Flutter, un framework complet dédié à la création d’apps mobiles multi-plateformes. C’est-à-dire qu’une seule codebase doit pouvoir être compilée pour toutes les plateformes (en l’occurrence, iOS, Android, Desktop et Web).

Dans un article dédié à leur découverte, je vais aborder l’écriture d’un composant relativement simple mais entièrement personnalisé. Il existe avec Flutter un ensemble de composants préétablis dans des bibliothèques comme Material ou Cupertino (respectivement prévues à destination d’Android ou iOS). Mais je voudrais afficher un élément de formulaire qui n’appartienne à aucun de ces 2 standards.

Aperçu du composant

Je tiens à préciser (mais j’imagine que ça sera clair par la suite) que je ne suis pas encore à l’aise avec toutes les notions de Flutter, et quelques erreurs peuvent se glisser dans cet article. Nous nous concentrerons surtout sur l’affichage, parce que c’est ce qui me parle le plus en tant qu’intégrateur.

Quelques précisions avant de démarrer

Nous voulons donc afficher un bloc à fond blanc sur toute la largeur de l’écran, contenant un label sur la gauche, suivi d’une valeur à droite qui pourra être éditée en appuyant sur tout le bloc. L’ensemble est souligné d’un discret trait gris qui délimitera visuellement plusieurs éléments de formulaire. Nous l’appellerons CustomFormInput.

Dans un formulaire que je ne détaillerai pas ici, nous voudrions pouvoir appeler un simple composant en lui passant les paramètres comme suit :

// Enfant d'un composant Column par exemple CustomFormInput(   label: "Email", // Simple chaîne de caractères   value: email, ), 

Importer un nouveau composant

De la même manière qu’une app Flutter utilise un package material avec une bibliothèque de composants par défaut (aux airs de Material Design) nous allons charger un nouveau fichier :

import 'package:flutter/material.dart';  import 'package:app_name/common/custom_form_input.dart'; // app_name fait référence à la racine de votre codebase 

Et nous créons dans la foulée un fichier custom_form_input.dart dans un dossier common (par exemple) qui nous permettra de centraliser d’autres composants du même acabit.

Écrire un nouveau composant

Comme dans le fichier précédent nous allons charger quelques composants par défaut dont nous pourrons hériter par la suite. Nous aurons besoin pour ce composant d’un « état » qui permet de récupérer des données d’un parent et de lui faire part des changements éventuels. Nous allons faire appel à la classe StatefulWidget et en hériter pour créer notre CustomFormInput :

import 'package:flutter/material.dart';  class CustomFormInput extends StatefulWidget {   final String label;   final String value;    CustomFormInput({Key key, this.label, this.value}) : super(key: key);    @override   _CustomFormInputState createState() => _CustomFormInputState(); } 

Comme précisé plus haut nous avons donc 2 propriétés label et value. Nous appelons ensuite notre constructeur tout juste déclaré, ses arguments étant liés à la classe courante avec this. Avec super nous écrasons l’attribut key de la classe parente. Celui-ci permet à FLutter de détecter quelle instance du widget a été modifiée dans une liste (à la manière de l’attribut key dans une liste en VueJS).

À la suite de la méthode @override (qui nous prévient au build si aucune méthode n’est écrasée) nous pouvons ensuite initialiser un state avec la méthode createState() que nous appellerons _CustomFormInputState.

État, done ; passons aux choses sérieuses

Je ne m’attarderai pas sur cette partie mais dans les grandes lignes nous définissons nos variables. On les initialise dans initState avec notamment notre contrôleur TextEditingController. Le dispose permet de nous assurer de libérer toutes les ressources qui auraient pu être utilisées par le contrôleur.

class _CustomFormInputState extends State<CustomFormInput> {   String _value ;   TextEditingController _controller;    void initState() {     _value = widget.value;     _controller = TextEditingController();     _controller.text = widget.value;     super.initState();   }    void dispose() {     _controller.dispose();     super.dispose();   }    @override   // here we'll override the class build method 

Affichage du composant

Nous allons englober notre composant dans une classe GestureDetector qui nous permet de définir une action au clic/tap avec onTap que nous appellerons _displayDialog et prend un seul widget comme enfant.

Pour obtenir la bordure en bas de notre bloc nous allons commencer par un widget DecoratedBox. Sa propriété decoration peut ainsi prendre comme valeur un widget BoxDecoration avec pour argument à la propriété border un widget Border. La méthode bottom de ce dernier prend quant à elle une valeur définie par le widget BorderSide dont les propriétés width et color auront respectivement les valeurs 1 et Color(0xFFD1D3DB) (soit la couleur hexadécimale #D1D3DB).

/* Petit parallèle pour intégrateurs web */ .CustomFormInput { border-bottom: 1px solid #D1D3DB; } 

Si vous avez compris le principe je vais me permettre d’accélérer un peu, nous avons ensuite un widget Padding, qui prend une valeur de padding et un enfant. Dans le widget Row, qui nous permet de placer nos éléments horizontalement, nous indiquons que les widgets enfants doivent être séparés les uns des autres avec MainAxisAlignment.spaceBetween (à la manière d’un align-items: space-bewteen en CSS).

Les enfants qui suivent n’ont pas de comportement à proprement parler, ils se soucient seulement d’afficher du texte avec une couleur customisée pour le label.

Widget build(BuildContext context) => GestureDetector(   onTap: () => _displayDialog(context),   child: DecoratedBox(     decoration: BoxDecoration(       border: Border(bottom: BorderSide(width: 1, color: Color(0xFFD1D3DB)))     ),     child: Padding(       padding: EdgeInsets.all(15.0),       child: Row(         mainAxisAlignment: MainAxisAlignment.spaceBetween,         children: <Widget>[           Text(             widget.label,             style: TextStyle(color: Color(0xFFA3A7B7), fontSize: 16)           ),           Text(             _value,             style: TextStyle(fontSize: 16)           )])),), ), // GestudeDetector end 

À la suite de cette méthode de build, nous allons déclarer la méthode _displayDialog que nous avions appelée dans la méthode onTap précédemment.

C’est assez simple, un widget showDialog permet de gérer la transition et le « fond » ou overlay de la modale qui viendra s’afficher au-dessus du contenu existant. Ce widget prend un context en premier argument, lui permettant de recevoir ou passer des données aux widgets qui le contiennent puis un widget Dialog en second argument.

Dans notre cas nous utilisons un AlertDialog qui permet d’afficher un contenu basique et quelques boutons. Ici nous aurons besoin d’un titre rappelant le champ sélectionné et d’un TextField pour éditer notre valeur email. Le bouton de validation se trouve dans l’attribut actions auquel nous passons un FlatButton qui, une fois pressé, modifie le champ et ferme le widget showDialog.

_displayDialog(BuildContext context) async {   return showDialog(     context: context,     builder: (context) {       return AlertDialog(         title: Text(widget.label),         content: TextField(           controller: _controller,         ),         actions: <Widget>[           FlatButton(             child: Text('OK'),             onPressed: () {               setState((){                 _value = _controller.text;               });               Navigator.of(context).pop();             },)],);     }); } 

En conclusion

Nous avons donc vu dans les grandes lignes comment créer et importer un composant, comment le faire réagir à une action de l’utilisateur, mais surtout en customiser l’affichage. J’espère que cet article vous aura donné envie d’essayer Flutter et vous aura fait découvrir quelques-uns de ses composants les plus utilisés.

À lire aussi

Diagnostiquer, comprendre et optimiser les performances d’une application React
4 mai 2026

Diagnostiquer, comprendre et optimiser les performances d’une application React

Lire la suite de l'article

Ouicommit Paris – IA : de l’expérimentation à l’industrialisation
15 avril 2026

Ouicommit Paris – IA : de l’expérimentation à l’industrialisation

Lire la suite de l'article

Ouidou et Scaleway : un partenariat stratégique pour accélérer le cloud souverain en Europe
8 avril 2026

Ouidou et Scaleway : un partenariat stratégique pour accélérer le cloud souverain en Europe

Lire la suite de l'article

Replay webinaire Ouidou x Sonar
2 juillet 2026

Replay webinaire Ouidou x Sonar

Lire la suite de l'article

Articles associés

Ouicommit Paris – IA : de l’expérimentation à l’industrialisation
15 avril 2026

Ouicommit Paris – IA : de l’expérimentation à l’industrialisation


Lire la suite
Ouidou et Scaleway : un partenariat stratégique pour accélérer le cloud souverain en Europe
8 avril 2026

Ouidou et Scaleway : un partenariat stratégique pour accélérer le cloud souverain en Europe


Lire la suite
Comment préparer votre Jira Cloud dès maintenant ? 
14 novembre 2025

Comment préparer votre Jira Cloud dès maintenant ? 


Lire la suite
Replay webinaire IA
5 novembre 2025

Replay webinaire IA


Lire la suite
  • Linkedin Ouidou
  • Youtube Ouidou

Blog Ouidou, le rendez-vous des équipes tech qui veulent comprendre avant de décider. Veille, retours d'expérience et décryptages pour rester à la pointe.

© 2026 Ouidou | Tous droits réservés | Plan du site | Mentions légales | Déclaration d'accessibilité
    Découvrir Ouidou
    No results See all results