StatefulWidget contre StatelessWidget.
StatelessWidget - Un widget qui ne nécessite pas d'état mutable.
Un widget sans état est un widget qui décrit une partie de l'interface utilisateur en créant une constellation d'autres widgets qui décrivent l'interface utilisateur plus concrètement. Le processus de construction se poursuit de manière récursive jusqu'à ce que la description de l'interface utilisateur soit entièrement concrète (par exemple, se compose entièrement de RenderObjectWidgets, qui décrivent des RenderObjects concrets).
Le stateless
widget est utile lorsque la partie de l'interface utilisateur que vous décrivez ne dépend de rien d'autre que des informations de configuration dans l'objet lui-même et du
BuildContext dans lequel le widget est gonflé. Pour les compositions qui peuvent changer dynamiquement, par exemple en raison d'un état d'horloge interne, ou en fonction d'un état du système, envisagez d'utiliser
StatefulWidget
.
class GreenFrog extends StatelessWidget {
const GreenFrog({ Key key }) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(color: const Color(0xFF2DBD3A));
}
}
StatefulWidget - Un widget dont l'état est modifiable.
- Les widgets avec état sont utiles lorsque la partie de l'interface utilisateur que vous décrivez peut changer dynamiquement.
Lorsque Flutter construit un StatefulWidget
, il crée un objet State. Cet objet est l'endroit où tout l'état mutable de ce widget est conservé.
Le concept d'État est défini par deux choses:
1) Les données utilisées par le widget peuvent changer.
2) Les données ne peuvent pas être lues de manière synchrone lorsque le widget est construit. (Tous les états doivent être établis au moment où la méthode de construction est appelée).
Cycle de vie StatefulWidget
Le cycle de vie comprend les étapes simplifiées suivantes:
- createState () - Lorsque Flutter est invité à créer un StatefulWidget, il appelle immédiatement
createState()
.
Crée l'état mutable pour ce widget à un emplacement donné dans l'arborescence.
Les sous-classes doivent remplacer cette méthode pour renvoyer une instance nouvellement créée de leur sous-classe State associée:
@override
_MyState createState() => _MyState();
- monté == true - Tous les widgets ont une
this.mounted
propriété booléenne . Cela devient vrai lorsque le buildContext
est attribué. C'est une erreur d'appeler setState
lorsqu'un widget est démonté. Si cet objet State est actuellement dans une arborescence.
Après avoir créé un objet State et avant l'appel initState
, le framework «monte» l'objet State en l'associant à un
BuildContext
. L'objet State reste monté jusqu'à l'
appel du framework dispose()
, après quoi le framework ne demandera plus jamais à l'
objet State de se reconstruire.
C'est une erreur d'appeler setState sauf si monté est vrai.
bool get mounted => _element != null;
- initState () - C'est la première méthode appelée lors de la création du widget (après le constructeur de classe, bien sûr).
initState
est appelée une et une seule fois. Il doit appelersuper.initState().
Initialisez les données qui reposent sur le BuildContext spécifique pour l'instance créée du widget.
Initialisez les propriétés qui reposent sur ces widgets «parents» dans l'arborescence.
Abonnez-vous à Streams ChangeNotifiers
ou à tout autre objet susceptible de modifier les données de ce widget.
@override
initState() {
super.initState();
cartItemStream.listen((data) {
_updateWidget(data);
});
}
- didChangeDependencies () - Appelé lorsqu'une dépendance de cet objet State change.
Cette méthode est également appelée immédiatement après initState
. Il est prudent d'appeler à BuildContext.inheritFromWidgetOfExactType
partir de cette méthode.
Les sous-classes remplacent rarement cette méthode car le framework appelle toujours build après les modifications de dépendance. Certaines sous-classes remplacent cette méthode car elles doivent effectuer un travail coûteux (par exemple, des récupérations de réseau) lorsque leurs dépendances changent, et ce travail serait trop coûteux à faire pour chaque construction.
@protected
@mustCallSuper
void didChangeDependencies() { }
- build () - Décrit la partie de l'interface utilisateur représentée par le widget.
Le framework appelle cette méthode dans un certain nombre de situations différentes:
- Après avoir appelé
initState
.
- Après avoir appelé
didUpdateWidget
.
- Après avoir reçu un appel à
setState
.
- Après une dépendance de cet objet State change (par exemple, un InheritedWidget référencé par les modifications de construction précédentes).
- Après avoir appelé disable, puis réinséré l'objet State dans l'arborescence à un autre emplacement.
Le framework remplace le sous-arbre sous ce widget par le widget retourné par cette méthode, soit en mettant à jour le sous-arbre existant, soit en supprimant le sous-arbre et en gonflant un nouveau sous-arbre, selon que le widget retourné par cette méthode peut mettre à jour la racine du sous-arbre existant , tel que déterminé par l'appel
Widget.canUpdate
.
En général, les implémentations renvoient une constellation nouvellement créée de widgets configurés avec les informations du constructeur de ce widget, le BuildContext donné et l'état interne de cet objet State.
@override
Widget build(BuildContext context, MyButtonState state) {
... () { print("color: $color"); } ...
}
- didUpdateWidget () - Appelé chaque fois que la configuration du widget change.
Si le widget parent se reconstruit et demande que cet emplacement dans l'arborescence se mette à jour pour afficher un nouveau widget avec le même type d'exécution et Widget.key, le framework mettra à jour la propriété widget de cet objet State pour faire référence au nouveau widget, puis l'appellera méthode avec le widget précédent comme argument.
Remplacez cette méthode pour répondre lorsque le widget change (par exemple, pour démarrer des animations implicites).
Le framework appelle toujours build après avoir appelé didUpdateWidget, ce qui signifie que tous les appels à setState dans didUpdateWidget sont redondants.
@mustCallSuper
@protected
void didUpdateWidget(covariant T oldWidget) { }
- setState () - Chaque fois que vous modifiez l'état interne d'un objet State, apportez le changement dans une fonction que vous passez à
setState
:
L'appel de setState notifie au framework que l'état interne de cet objet a changé d'une manière qui pourrait avoir un impact sur l'interface utilisateur dans cette sous-arborescence, ce qui oblige le framework à planifier une génération pour
cet objet State.
Si vous modifiez simplement l'état directement sans appeler setState , le framework peut ne pas planifier une génération et l'interface utilisateur de cette sous-arborescence peut ne pas être mise à jour pour refléter le nouvel état.
setState(() { _myState = newValue });
- deactivate () - Deactivate est appelé lorsque State est supprimé de l'arborescence, mais il peut être réinséré avant la fin du changement de cadre actuel. Cette méthode existe essentiellement parce que les objets State peuvent être déplacés d'un point dans une arborescence à un autre.
- Le framework appelle cette méthode chaque fois qu'il supprime cet objet State de l'arborescence. Dans certains cas, le cadre réinsère l'objet State dans une autre partie de l'arborescence (par exemple, si le sous-arbre contenant cet objet State est greffé d'un emplacement dans l'arborescence à un autre). Si cela se produit, le framework s'assurera qu'il appelle build pour donner à l'objet State une chance de s'adapter à son nouvel emplacement dans l'arborescence. Si le framework réinsère ce sous-arbre, il le fera avant la fin de l'image d'animation dans laquelle le sous-arbre a été supprimé de l'arborescence. Pour cette raison, les objets State peuvent différer la libération de la plupart des ressources jusqu'à ce que l'infrastructure appelle leur méthode dispose.
Ceci est rarement utilisé.
@protected
@mustCallSuper
void deactivate() { }
- dispose () - Appelé lorsque cet objet est supprimé définitivement de l'arborescence.
Le framework appelle cette méthode lorsque cet objet State ne sera plus jamais généré. Après les appels du framework dispose()
, l'objet State est considéré comme non monté et la propriété montée est false. L'appel de setState à ce stade est une erreur. Cette étape du cycle de vie est terminale: il n'y a aucun moyen de remonter un objet State qui a été supprimé.
Les sous-classes doivent remplacer cette méthode pour libérer toutes les ressources conservées par cet objet (par exemple, arrêter toutes les animations actives).
@protected
@mustCallSuper
void dispose() {
assert(_debugLifecycleState == _StateLifecycle.ready);
assert(() { _debugLifecycleState = _StateLifecycle.defunct; return true; }());
}
Pour plus d'informations, cliquez ici , ici