CSS Animations vs Transitions: What’s the Difference

Transitions and animations both create motion in CSS, but they solve different problems — one responds to a state change, the other runs independently on its own timeline.

/* Transition: animates a property change between two states */
.button {
    background: #3858e9;
    transition: background 0.2s ease, transform 0.2s ease;
}
.button:hover {
    background: #183ad6;
    transform: translateY(-2px);
}

/* Animation: runs on its own, with multiple keyframe steps */
@keyframes pulse {
    0%, 100% { opacity: 1; }
    50% { opacity: 0.5; }
}

.loading-indicator {
    animation: pulse 1.5s ease-in-out infinite;
}

Use a transition for simple “from state A to state B” changes (hover, focus, a toggled class), and an animation when you need multiple steps, looping, or motion that isn’t triggered by a state change at all — a loading spinner has nothing to transition from, so it needs @keyframes.