TransitionsGratuit

Elastic Spring

Une balle de 50 px qui saute à 60 px, retombe en s'écrasant (1,15 × 0,85), rebondit à 25 puis 8 px et se pose, en 2 s : une seule keyframe CSS dont la courbe dépasse sa cible à chaque étape, d'où l'élasticité — zéro JavaScript, une simple pulsation si l'utilisateur réduit les animations.

CSSPhysiqueRebond

Mis à jour le

Survolez ou cliquez la scène pour interagir

Cet effet est gratuit — la catégorie Transitions en contient 52 au total, dont 9 gratuits. Effect.Labs regroupe 840 effets vanilla. Découvrir la catégorie →

Exemples d'usage

Jeudi, 15 h 40Chambre 12 · M. Garnier

Léa

votre petite-fille vous appelle

En communication · 00:47

① Appel d'un proche — tablette simplifiée d'un résident d'EHPAD

QuandLa petite-fille appelle : la pastille avec sa photo rebondit au-dessus de son prénom ; dès que le résident touche « Décrocher », la pastille s'immobilise et le compteur d'appel démarre.
PourquoiLe rebond élastique attire l'œil comme une sonnerie visuelle, utile quand l'ouïe baisse ; l'immobilité dit que l'appel est pris, sans autre message.
RéglagesBalle agrandie à 96 px, bord blanc de 4 px et portrait dessiné en dégradés ; keyframe et durée d'origine (2 s, sauts de 60, 25 et 8 px) ; boutons de 52 px de haut, texte en 20 px ; état B : animation: none sur la pastille.

À toi, Jules !Touche le dé pour le lancer

4 ! Avance de 4 casesL'oie te fait rejouer

Lancer le dé
171819202122 oie23

② Dé en attente du lancer — jeu de l'oie numérique pour enfants

QuandC'est le tour de Jules : le dé saute sur place au-dessus du plateau ; il le touche, le dé se pose sur 4 et la case d'arrivée s'entoure de pointillés.
PourquoiL'écrasement et l'étirement donnent au dé une matière de jouet en caoutchouc, et l'enfant comprend, sans lire, que c'est à lui de jouer.
RéglagesÉlément de 72 px aux coins de 16 px (border-radius à la place du cercle), fond blanc et points bleus ; même rebond ; au lancer, animation: none et la face passe de 5 à 4.
1 h 02assis depuis la réunion de 10 h
3 / 5pauses prises aujourd'hui

Et si on se levait ?

3 minutes : épaules, dos, un verre d'eau

2:47

Roulez les épaules vers l'arrière, 10 fois

③ Invitation à se lever — appli de pauses actives en télétravail

QuandAprès une heure assis, la carte de rappel s'ouvre avec une balle verte qui rebondit sur un trait de sol ; « Lancer la pause » l'arrête et affiche le compte à rebours de 3 minutes.
PourquoiUne balle qui saute donne envie de bouger, sans alarme ni son agressif ; elle s'arrête quand la pause commence, comme si elle passait le relais.
RéglagesBalle de 62 px en dégradé vert pomme, posée au-dessus d'un trait de 3 px qui figure le sol ; rebond d'origine ; état B : balle immobile, chronomètre en 30 px.

Comment ça marche

Trois éléments : le cadre .md-spring-stage (250 px de haut, fond #1a1a24), la zone .md-spring qui centre, et .md-spring-ball, un disque de 50 px en dégradé indigo vers rose (#6366f1 → #ec4899). Toute la physique tient dans @keyframes mdSpring, jouée en boucle : animation: mdSpring 2s cubic-bezier(0.34, 1.56, 0.64, 1) infinite. Les étapes alternent sauts et contacts : 20 % en l'air à −60 px, étirée (0,9 × 1,1) ; 40 % au sol, écrasée (1,15 × 0,85) ; 55 % à −25 px ; 70 % au sol (1,05 × 0,95) ; 85 % à −8 px ; 100 % au repos. Chaque rebond fait à peu près 40 % du précédent, et les déformations diminuent avec lui : c'est ce qui donne l'impression d'une matière qui amortit.

La courbe fait le reste. Sa deuxième valeur, 1,56, dépasse 1 : entre deux étapes, la balle va un peu plus loin que la cible avant d'y revenir. Mesuré image par image dans Chromium 151 : sommet du premier saut à −65,8 px au lieu de −60, enfoncement de 5,8 px sous le point de repos au contact, écrasement maximal 1,17 × 0,83. Ce dépassement, appliqué à chaque segment, joue le rôle du ressort ; avec une courbe ease-in-out, la même keyframe donnerait une balle qui monte et descend sans rebondir. L'origine de la transformation reste au centre : à l'écrasement, la balle se tasse vers son milieu et son bas remonte d'environ 4 px — voir les réglages pour la poser sur un sol. Le transform seul est animé, sans recalcul de mise en page.

L'effet est un appel à l'attention qui tourne en boucle, pas une transition entre deux états : il bouge tant que quelque chose attend une action. C'est à votre page de l'arrêter quand l'action a lieu (appel décroché, dé lancé) : animation: none sur la balle la remet au repos, comme dans les trois exemples. Le cadre a sa propre classe, préfixée comme le reste de l'effet : deux effets de la bibliothèque collés sur la même page ne se réécrivent pas.

Accessibilité

  • Mouvement réduit : sous prefers-reduced-motion: reduce, la keyframe de rebond est remplacée par mdSpringFade, une pulsation d'opacité de 1 à 0,45 sur le même rythme de 2 s. Mesuré dans Chromium 151, Firefox 153 et WebKit 26 : plus aucun déplacement ni déformation (transformation identique à chaque mesure), opacité qui varie. Le signal « quelque chose attend » reste lisible sans mouvement.
  • Arrêt : un mouvement qui dure plus de 5 secondes doit pouvoir s'arrêter. Ici, l'arrêt naturel est l'action attendue elle-même (décrocher, lancer, démarrer) : posez animation: none dès qu'elle a lieu, et ne laissez pas la balle rebondir dans une zone de la page qui n'attend rien.
  • Sens : la balle est un div vide, sans rôle. Si elle signale un appel ou un tour de jeu, écrivez-le aussi en texte à côté (« Léa vous appelle ») ; si elle sert de bouton, donnez-lui role="button", tabindex="0" et un libellé, ou mettez-la dans un vrai button.
  • Contraste : le dégradé indigo-rose ressort à plus de 3:1 sur le fond #1a1a24 du cadre ; sur un fond clair, vérifiez la teinte indigo, la plus sombre.

Compatibilité navigateur

CSS pur (@keyframes, transform, cubic-bezier avec une valeur hors de 0-1), 1,4 Ko, zéro JavaScript. Mesuré dans Chromium 151, Firefox 153 et WebKit 26 : même rebond, même pulsation de remplacement sous mouvement réduit. Une courbe cubic-bezier dont l'ordonnée dépasse 1 est valide dans la norme et lue par les trois moteurs.

Chrome 43+✓ Complet
Firefox 16+✓ Complet
Safari 9+✓ Complet
Edge 12+✓ Complet
Mobile iOS 9+✓ Complet
Android Chrome 43+✓ Complet

Sans animations CSS, la balle reste immobile au centre de son cadre, ronde et en couleur : l'élément se voit, seul le rebond manque.

Le code

Copiez les trois blocs dans votre page. Aucune dépendance.

HTML
<div class="md-spring-stage">
  <div class="md-spring">
    <div class="md-spring-ball"></div>
  </div>
</div>
CSS
.md-spring-stage,
.md-spring-stage *,
.md-spring-stage *::before,
.md-spring-stage *::after {
  box-sizing: border-box
}

.md-spring-stage {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 100%;
  height: 250px;
  overflow: hidden;
  position: relative;
  background: rgb(26, 26, 36);
  color: rgb(255, 255, 255);
  font-family: sans-serif;
}

.md-spring {
  width: 100%;
  height: 100%;
  display: flex;
  align-items: center;
  justify-content: center;
}

.md-spring-ball {
  width: 50px;
  height: 50px;
  border-radius: 50%;
  background: linear-gradient(135deg, #6366f1, #ec4899);
  animation: mdSpring 2s cubic-bezier(0.34, 1.56, 0.64, 1) infinite;
}

@keyframes mdSpring {

  0%,
  100% {
    transform: translateY(0) scaleX(1) scaleY(1);
  }

  20% {
    transform: translateY(-60px) scaleX(0.9) scaleY(1.1);
  }

  40% {
    transform: translateY(0) scaleX(1.15) scaleY(0.85);
  }

  55% {
    transform: translateY(-25px) scaleX(0.95) scaleY(1.05);
  }

  70% {
    transform: translateY(0) scaleX(1.05) scaleY(0.95);
  }

  85% {
    transform: translateY(-8px);
  }
}

/* Mouvement réduit : ni saut ni déformation, une pulsation d'opacité garde le signal */
@media (prefers-reduced-motion: reduce) {
  .md-spring-ball {
    animation: mdSpringFade 2s ease-in-out infinite;
  }
}

@keyframes mdSpringFade {

  0%,
  100% {
    opacity: 1;
  }

  50% {
    opacity: 0.45;
  }
}
JavaScript (fx-0726)

Personnaliser

Options passées à l'API ou attributs data-* :

Option / propriétéDéfautEffet
Hauteur des sauts (CSS — translateY à 20 %, 55 % et 85 %) −60 / −25 / −8 px Gardez un rapport proche de 0,4 entre deux rebonds pour un amorti crédible : −90 / −36 / −14 px pour une balle plus grande. Des sauts égaux donnent une balle qui ne perd jamais d'énergie.
Écrasement et étirement (CSS — scaleX / scaleY) 1,15 × 0,85 au premier contact, 0,9 × 1,1 en l'air 1,3 × 0,7 donne une matière très molle (gelée) ; 1,05 × 0,95 une balle de tennis. Gardez le produit des deux proche de 1 pour que la balle semble garder son volume.
Courbe (CSS — cubic-bezier(0.34, 1.56, 0.64, 1)) dépassement d'environ 10 % 1,56 → 1,9 accentue le ressort (sommet plus haut, enfoncement plus marqué) ; 1,56 → 1 supprime le dépassement et le côté élastique.
Durée (CSS — 2s) 2 s par cycle complet 1,4 s rend la balle nerveuse ; 3 s plus lourde. Pour un rebond suivi d'une vraie pause, étirez la keyframe : terminez les étapes à 60 % et laissez la balle au repos jusqu'à 100 %.
Arrêt (CSS — animation: none) aucun : boucle infinie Posé par une classe d'état (ex. .is-answered .md-spring-ball), il remet la balle au repos immédiatement. Pour finir le saut en cours, attendez l'évènement animationiteration avant de poser la classe.
Taille et couleur (CSS — .md-spring-ball) 50 px, dégradé #6366f1 → #ec4899 Tout élément peut rebondir : photo, icône, dé. Les distances étant en pixels, une balle de 100 px garde des sauts de 60 px ; augmentez-les avec la taille.

FAQ

Comment arrêter le rebond quand l'utilisateur agit ?

Ajoutez une classe d'état sur un parent et la règle .is-done .md-spring-ball { animation: none; } : la balle revient aussitôt au repos. Si le saut est coupé en plein vol et que cela se voit, écoutez animationiteration sur la balle et posez la classe à ce moment-là, quand elle touche le sol en fin de cycle. Pour relancer, retirez la classe : l'animation repart du début.

Pourquoi la balle s'enfonce-t-elle un peu sous son point de départ ?

C'est la courbe cubic-bezier(0.34, 1.56, 0.64, 1) : sa deuxième valeur dépasse 1, donc chaque segment va plus loin que sa cible avant d'y revenir. Mesuré : 5,8 px sous le repos au contact, sommet à 65,8 px au lieu de 60. C'est ce dépassement qui fait « ressort ». Si la balle est posée sur un trait de sol et que l'enfoncement se voit, remontez le sol de 6 px ou réduisez 1,56 à 1,3.

Comment l'écraser contre le sol plutôt qu'au milieu ?

Ajoutez transform-origin: 50% 100% à .md-spring-ball. Par défaut, l'écrasement se fait autour du centre : au contact, le bas de la balle remonte d'environ 4 px et elle semble flotter. Avec l'origine en bas, le bas reste collé au sol et seule la hauteur s'aplatit, comme une vraie balle. Les sauts (translateY) ne changent pas.