ui-package

Par verygoodopensource · vgv-ai-flutter-plugin

Bonnes pratiques pour créer un package Flutter UI au-dessus de Material — composants personnalisés, thématisation basée sur `ThemeExtension`, API cohérentes et tests de widgets. Compatible avec le template `app_ui_package`.

npx skills add https://github.com/verygoodopensource/vgv-ai-flutter-plugin --skill ui-package

UI Package

Bonnes pratiques pour créer un package UI Flutter — une bibliothèque de widgets réutilisables qui s'appuie sur package:flutter/material.dart, l'étendant avec des composants spécifiques à l'application, des tokens de design personnalisés via ThemeExtension, et une surface API cohérente.

Fondation de thématisation : Cette skill se concentre sur la structure du package UI, les APIs des widgets et les tests. Pour la thématisation Material 3 fondamentale (ColorScheme, TextTheme, thèmes de composants, constantes d'espacement, mode clair/sombre), consultez la skill Material Theming (/material-theming). Les deux skills sont complémentaires — Material Theming couvre comment configurer et utiliser ThemeData ; cette skill couvre comment l'étendre avec des tokens ThemeExtension et packager les widgets réutilisables autour.

Standards Essentiels

Appliquez ces standards à TOUS les travaux de package UI :

  • Construire sur Material — dépendre de flutter/material.dart et composer des widgets Material ; ne pas reconstruire les primitives que Material fournit déjà
  • Un widget par fichier — chaque widget public vit dans son propre fichier nommé d'après le widget en snake_case (p. ex., app_button.dart)
  • Fichier barrel pour l'API publique — exposer tous les widgets publics et les classes de thème via un seul fichier barrel (p. ex., lib/my_ui.dart) qui ré-exporte aussi material.dart
  • Étendre la thématisation avec ThemeExtension — utiliser ThemeData, ColorScheme, et TextTheme de Material comme base (consultez la skill Material Theming) ; ajouter des tokens spécifiques à l'application (espacement, couleurs personnalisées) via ThemeExtension<T>
  • Chaque widget a un test de widget correspondant — les tests comportementaux vérifient les interactions, les callbacks et les changements d'état
  • Préfixer toutes les classes publiques — utiliser un préfixe cohérent (p. ex., App, Vg) pour éviter les collisions de noms avec les widgets Material
  • Utiliser des constructeurs const partout où c'est possible — tous les constructeurs de widget doivent être const quand c'est réalisable
  • Documenter chaque membre public — chaque classe publique, paramètre de constructeur et méthode a un commentaire dartdoc

Structure du Package

my_ui/
├── lib/
│   ├── my_ui.dart              # Fichier barrel — ré-exporte material.dart + toute l'API publique
│   └── src/
│       ├── theme/
│       │   ├── app_theme.dart        # Classe AppTheme avec builders ThemeData clair/sombre
│       │   ├── app_colors.dart       # AppColors ThemeExtension pour les tokens de couleur personnalisés
│       │   ├── app_spacing.dart      # AppSpacing ThemeExtension pour les tokens d'espacement
│       │   └── app_text_styles.dart  # Optionnel : styles de texte supplémentaires au-delà du TextTheme de Material
│       ├── widgets/
│       │   ├── app_button.dart
│       │   ├── app_text_field.dart
│       │   ├── app_card.dart
│       │   └── ...
│       └── extensions/
│           └── build_context_extensions.dart  # Raccourcis context.appColors, context.appSpacing
├── test/
│   ├── src/
│   │   ├── theme/
│   │   │   └── app_theme_test.dart
│   │   └── widgets/
│   │       ├── app_button_test.dart
│   │       └── ...
│   └── helpers/
│       └── pump_app.dart         # Utilitaire de test encapsulant les widgets dans MaterialApp + thème
├── widgetbook/                   # Sous-module catalogue Widgetbook (sandbox + showcase)
│   └── ...
└── pubspec.yaml

Construction de Widgets

Directives d'API Widget

  • Composer des widgets Material — utiliser FilledButton, OutlinedButton, TextField, Card, etc. comme éléments de base
  • Accepter uniquement les paramètres strictement nécessaires — éviter les constructeurs « fourre-tout »
  • Utiliser des paramètres nommés pour tout sauf key et child/children
  • Fournir des valeurs par défaut sensées dérivées du thème quand un paramètre n'est pas fourni
  • Exposer les callbacks avec ValueChanged<T> ou VoidCallback — ne pas utiliser Function brute
  • Utiliser Widget? pour la composition optionnelle basée sur des emplacements (icônes principales, finales, etc.)

Anti-Patterns

Anti-Pattern Approche Correcte
Reconstruire des widgets que Material fournit déjà (p. ex., bouton personnalisé à partir de GestureDetector + DecoratedBox) Composer des widgets Material (FilledButton, OutlinedButton) et les styler
Créer un système de thème parallèle avec InheritedWidget personnalisé Utiliser ThemeData de Material comme base et ThemeExtension pour les tokens personnalisés
Coder en dur Color(0xFF...) dans le code du widget Utiliser Theme.of(context).colorScheme pour les couleurs standard et context.appColors pour les tokens personnalisés
Dupliquer les rôles de ColorScheme de Material dans une classe personnalisée Créer uniquement des tokens ThemeExtension pour les valeurs que Material ne couvre pas (p. ex., succès, avertissement, info)
Utiliser dynamic ou Object pour les types de callback Utiliser VoidCallback, ValueChanged<T> ou des typedefs de fonction spécifiques
Exposer directement les fichiers d'implémentation interne Utiliser un fichier barrel ; garder tous les fichiers sous src/ privés

Création du Package

Utiliser l'outil MCP Very Good CLI pour scaffolder le app_ui_package.

Skills similaires