Utilisation des comportements Qt Quick avec les états
Utilisation des comportements avec les états
Dans certains cas, vous pouvez choisir d'utiliser un comportement pour animer un changement de propriété causé par un changement d'état. Si cela fonctionne bien dans certaines situations, dans d'autres, cela peut conduire à un comportement inattendu.
Voici un exemple qui illustre le problème :
import QtQuick 2.0 Rectangle { width: 400 height: 400 Rectangle { id: coloredRect width: 100 height: 100 anchors.centerIn: parent color: "red" Behavior on color { ColorAnimation {} } MouseArea { id: mouser anchors.fill: parent hoverEnabled: true } states: State { name: "GreenState" when: mouser.containsMouse PropertyChanges { target: coloredRect color: "green" } } } }
En testant l'exemple en déplaçant rapidement et de manière répétée la souris dans et hors du rectangle coloré, on constate que le rectangle coloré prend une couleur verte au fil du temps, sans jamais revenir au rouge intégral. Ce n'est pas ce que nous voulions ! Le problème vient du fait que nous avons utilisé un comportement pour animer le changement de couleur et que notre changement d'état est déclenché par l'entrée ou la sortie de la souris sur le site MouseArea, ce qui peut facilement être interrompu.
Pour formuler le problème de manière plus formelle, l'utilisation conjointe d'États et de Comportements peut entraîner un comportement inattendu dans les cas suivants :
- un comportement est utilisé pour animer un changement de propriété, en particulier lors du passage d'un état explicitement défini à l'état de base implicite ; et
- ce comportement peut être interrompu pour (ré)entrer dans un état explicitement défini.
Le problème se pose en raison de la manière dont l'état de base est défini pour QML : comme l'état "instantané" de l'application juste avant d'entrer dans un état explicitement défini. Dans ce cas, si nous sommes en train d'animer le vert vers le rouge et que nous interrompons l'animation pour revenir à "l'état vert", l'état de base inclura la couleur dans sa forme intermédiaire, au milieu de l'animation.
Bien que les futures versions de QML devraient être en mesure de gérer cette situation de manière plus gracieuse, il existe actuellement plusieurs façons de retravailler votre application afin d'éviter ce problème.
1. Utilisez une transition pour animer le changement, plutôt qu'un comportement.
import QtQuick 2.0 Rectangle { width: 400 height: 400 Rectangle { id: coloredRect width: 100 height: 100 anchors.centerIn: parent color: "red" MouseArea { id: mouser anchors.fill: parent hoverEnabled: true } states: State { name: "GreenState" when: mouser.containsMouse PropertyChanges { target: coloredRect color: "green" } } transitions: Transition { ColorAnimation {} } } }
2. Utiliser une liaison conditionnelle pour modifier la valeur de la propriété, plutôt qu'un état.
import QtQuick 2.0 Rectangle { width: 400 height: 400 Rectangle { id: coloredRect width: 100 height: 100 anchors.centerIn: parent color: mouser.containsMouse ? "green" : "red" Behavior on color { ColorAnimation {} } MouseArea { id: mouser anchors.fill: parent hoverEnabled: true } } }
3. Utiliser uniquement des états explicitement définis, plutôt qu'un état de base implicite.
import QtQuick 2.0 Rectangle { width: 400 height: 400 Rectangle { id: coloredRect width: 100 height: 100 anchors.centerIn: parent Behavior on color { ColorAnimation {} } MouseArea { id: mouser anchors.fill: parent hoverEnabled: true } states: [ State { name: "GreenState" when: mouser.containsMouse PropertyChanges { target: coloredRect color: "green" } }, State { name: "RedState" when: !mouser.containsMouse PropertyChanges { target: coloredRect color: "red" } }] } }
© 2026 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.