VueJS - Tweezing et Motion : les transitions et animations rendues plus simples et naturelles

Le 29 juin dernier (2018) se déroulait un meetup VueJS à Paris sur le même modèle que l’événement à Amsterdam les 14 et 15 février précédents, en néanmoins plus modeste. 

Il s’agissait principalement de conférences sur les dernières nouveautés proposées par Vue2 ainsi que les modules et frameworks phares gravitant autour de celui-ci.

Comment utiliser les modules VueJs Tweezing et Motion ?

VueJs propose à l’heure actuelle deux composants que sont <transition> et <transition-group> permettant de réaliser des transitions CSS assez facilement en réaction, principalement, aux changements des attributs v-if et v-show. Ces composants restent assez limités et ne permettent pas de faire réagir une animation à un changement d’état, par exemple modifier la durée ou la position temporelle de l’animation en réaction au changement de la valeur d’un slider, ou encore faire suivre le curseur de la souris à un élément HTML. Retrouvez les slides.

Trouver le juste équilibre entre animation et expérience utilisateur

Eduardo San Martin Morote, membre de la core team de VueJs, nous propose une réponse à ces problèmes sous la forme du package Tweezing. Il commence par rappeler l’importance et les risques des animations qui peuvent tout autant rendre une expérience beaucoup plus claire et fluide que la détruire totalement, faisant fermer la page ou l’application aussitôt. En résumé, les animations doivent être rapides, avoir une utilité, et ne pas gêner la lecture ou simplement rendre un élément plus vivant et “fun”, du moment qu’il ne dégrade pas l’expérience utilisateur.

State-animations

L’intérêt de ce qu’Eduardo appelle des state-animations est de pouvoir réagir à des changements de valeur. Par exemple, un booléen passant de True à False pourra animer la couleur d’un bouton sans avoir à influer sur sa visibilité via v-if ou v-show comme il le faudrait avec le composant <transition> natif à Vue. Eduardo nomme les trois manières qu’il voit pour effectuer une transition :

  • Class switching
  • Easing via Tween
  • Physique (springing)

Le class switching est déjà possible via l’attribut :class ; il n’est donc pas intéressant de le développer ici.

L’easing sans utiliser JavaScript

Jusque-là pour y parvenir il fallait soit passer par des transitions/animations CSS qui restent très limitées, soit utiliser un moteur de Tween externe et coder l’animation en JavaScript. Tweezing devient puissant lorsqu’il va permettre d’utiliser un moteur de Tween, sans pour autant utiliser JavaScript, par le biais du composant <Tweezing> qui va exposer les propriétés du moteur de Tween en attributs de composant. Ceci permettra de contrôler le Tween simplement en changeant des valeurs comme on le ferait pour n’importe quelle autre valeur de formulaire par exemple.

Le springing (changements physiques) pour un effet d’élasticité

Le problème des Tween classiques est que si l’on souhaite changer la destination d’un objet avant la fin de l’animation, on peut obtenir une sensation de saccade puisque l’animation recommencera de zéro. A vrai dire, dans la plupart des cas, seuls les yeux les plus aguerris verront réellement le problème, les autres se contenteront au mieux de le ressentir. Dans des cas plus extrêmes le problème pourra être bien plus notable. Voici une équation très classique pour pallier cela :

position += (destination - position) * coefficient

 (Plus le coefficient est petit plus l’objet mettra du temps à arriver à destination) Voici un exemple : Si, au lieu de faire un Tween classique, on utilise cette formule pour interpoler une valeur, alors les changements de destination seront plus fluides et naturels. C’est l’idée des déplacements dits “physiques”. Là où Eduardo va un peu plus loin, c’est qu’au lieu d’utiliser cette simple formule, comparable à un Sine.easeOut utilisé au-dessus, il va avoir recours à une formule dite de “springing”, qui permet par exemple de créer un effet d’élasticité. Via 3 paramètres on pourra définir plusieurs effets s’approchant des easing de Quad, Quart, Sine, Back, Bounce ou encore Elastic, à la différence près qu’elles supporteront les changements de destination de manière plus lisse et naturelle. La différence majeure avec les Tweens classiques est qu’on ne peut plus parler de durée de transition. En effet, la durée dépend de la distance entre la valeur de début, la valeur de fin, et les 3 paramètres. A aucun moment on ne définira de durée de transition. Voici, pour mieux visualiser la différence, un exemple de l’auteur de ce composant : https://state-animations-amsterdam.surge.sh/sudoku/ https://state-animations-amsterdam.surge.sh/sudoku-motion/ Si on clique sur “shuffle” de manière rapide et répétée, on peut voir que la seconde version est plus fluide dans les changements d’état que la première basée sur des Tweens.

Composant Vue-Tweezing

Passons à Tweezing à proprement parler avec quelques exemples. Le premier exemple met en pratique l’utilisation d’un tween via un composant VueJs :

<Tweezing
:to="endValue"
 :duration="tweenDuration"

:easing="easingType"
> 
<div class="circle"></div>
</Tweezing>

Ainsi, toute mise à jour de l’une des valeurs “endValue”, “tweenDuration” ou “easingType” relancera le Tween automatiquement sans rien avoir à faire. Il n’est à aucun moment nécessaire de créer le moindre Tween via code. Ce qui, selon les librairies de Tween, peut représenter une économie drastique de code. Il est également possible si besoin de contrôler le Tween en accédant à son instance. Par exemple, pour stopper un Tween :

$refs.tweezing.$tween.stop()

Source : https://github.com/posva/vue-tweezing

Composant Vue-Motion

Le composant Vue-Motion sera le pendant de Tweezing mais pour l’équation de springing évoqué plus haut. Il aura donc la tâche de rendre le plus simple possible le fait d’appliquer une transition “physique” à un ou plusieurs objets. Voici un exemple de mise en pratique :

<Motion :value="offset" tag="div">
 <div
slot-scope="props"
:style="{ transform: 'translateX(${props.value}px)' }"></div>
</Motion>

Toute modification de la valeur “offset” entraînera un changement de destination X à l’élément DIV. Il est également possible de modifier les 3 valeurs de Stiffness, Damping et Precision pour paramétrer l’effet de déplacement afin qu’il soit par exemple plus ou moins élastique. Source : https://github.com/posva/vue-motion

Et après ?

Si ces composants fonctionnent bien en l’état, ils n’en sont pas moins qu’à un stade expérimental depuis plusieurs mois, l’auteur de ceux-ci étant très demandeur de feedback et de contributions pour les améliorer et les stabiliser si besoin, afin d’éventuellement en faire des composants natifs à Vue. Dans un prochain article, nous reviendrons sur la conférence de Guillaume Chau au VueJS 2018 à propos de Vue-Apollo et comment il intègre GraphQL, grâce à Apollo, au sein de VueJS.  

Auteur : François Dursus, Creative Developer, Le Lab SQLI