Master CSS Animations: From Simple Transitions to Advanced SVG Loading Effects

This article provides a comprehensive guide to CSS animation techniques, covering basic transition and animation properties, continuous scrolling, bounce effects, like button bursts, SVG‑based loading and progress bars, typing simulations, frame‑by‑frame sprite animations, and the use of steps() for timing control, all illustrated with practical code examples.

Aotu Lab
Aotu Lab
Aotu Lab
Master CSS Animations: From Simple Transitions to Advanced SVG Loading Effects

Introduction

Web developers often choose between CSS3 transition / animation, setInterval / setTimeout, and requestAnimationFrame for creating animations. For most cases, CSS3 animation offers the best balance of performance and development efficiency.

Common Animation Properties

The article first lists the most frequently used CSS animation properties and then demonstrates several practical demos.

Continuous Scrolling Demo

By animating the transform: translateY of a container, a seamless vertical scrolling effect is achieved. The keyframe definition and CSS rules are:

@keyframes scroll {
  0% { transform: translate(0, 0); }
  100% { transform: translate(0, -$height); }
}
.ul {
  animation-name: scroll;
  animation-duration: 5s;
  animation-timing-function: linear;
  animation-iteration-count: infinite;
}

To keep the scroll continuous, duplicate content is added at the end of the list.

Bounce Effect

The bounce animation splits the motion into multiple stages, adjusting the top property at each keyframe. A custom cubic‑bezier curve smooths the motion, and animation-fill-mode: forwards preserves the final state.

@keyframes animate {
  0% { top: -100%; opacity: 0; }
  25% { top: 60%; opacity: 1; }
  50% { top: 48%; opacity: 1; }
  75% { top: 52%; opacity: 1; }
  100% { top: 50%; opacity: 1; }
}
.popup {
  animation-name: animate;
  animation-duration: 0.5s;
  animation-timing-function: cubic-bezier(0.21, 0.85, 1, 1);
  animation-iteration-count: 1;
  animation-fill-mode: forwards;
}

Like Button Burst Effect

A combination of two @keyframes animations—one for vertical movement and one for horizontal jitter—creates a lively burst when a user clicks the like button. The animations are applied to a dynamically created .bubble element, which is removed after a short timeout.

@keyframes animation-y {
  0% { transform: translate(-50%, 100px) scale(0); }
  50% { transform: translate(-50%, -100px) scale(1.5); }
  100% { transform: translate(-50%, -300px) scale(1.5); }
}
@keyframes animation-x {
  0% { margin-left: 0px; }
  25% { margin-left: 25px; }
  75% { margin-left: -25px; }
  100% { margin-left: 0px; }
}
.bubble {
  animation: animation-x 3s -2s linear infinite, animation-y 4s 0s linear 1;
}
function like() {
  const likeDom = document.createElement('div');
  likeDom.className = 'bubble';
  document.body.appendChild(likeDom);
  setTimeout(() => { document.body.removeChild(likeDom); }, 4000);
}

SVG Loading / Progress Bar

Using an SVG circle with stroke-dasharray and stroke-dashoffset, a circular loading animation is built. The dash array is set to the circle’s circumference (≈157) and the offset is animated from 0 to –157 (or –207 for a full‑cycle progress bar).

@keyframes loading {
  0% { stroke-dashoffset: 0; }
  100% { stroke-dashoffset: -157; }
}
circle { animation: loading 1s 0s ease-out infinite; }

Using steps() for Timing Control

The steps() function defines a stepped timing function for animation-timing-function. It accepts a step count and an optional start or end keyword, allowing precise control over when keyframes are applied.

animation-timing-function: steps(5, start);

Typing Effect

By setting the container width to match the total character width and applying steps(N) where N equals the number of characters, a typewriter animation is achieved. Consistent character width is ensured by using the Monaco font.

@keyframes animate-x { 0% { width: 0; } }
p {
  width: 125px; /* 13 chars × ~9.6px */
  overflow: hidden;
  border-right: 1px solid transparent;
  animation: animate-x 3s 0s steps(13) 1 forwards, cursor-x 0.4s linear infinite;
}

Frame‑by‑Frame Sprite Animation

A 47‑frame sprite sheet is animated by shifting the background-position of a .main element. The steps(47) timing function synchronizes the background movement with the frame count.

@keyframes animate {
  0% { background-position: 0 0; }
  100% { background-position: 0 100%; }
}
.main {
  width: 260px;
  height: 200px;
  background: url(<em>sprite.png</em>) no-repeat;
  background-size: 100%;
  animation: animate 2s 1s steps(47) infinite alternate;
}

References

W3Schools CSS Reference

MDN "will-change" documentation

Various CodePen demos linked in the original article

animationWebSVGCSSkeyframessteps
Aotu Lab
Written by

Aotu Lab

Aotu Lab, founded in October 2015, is a front-end engineering team serving multi-platform products. The articles in this public account are intended to share and discuss technology, reflecting only the personal views of Aotu Lab members and not the official stance of JD.com Technology.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.