CSS Transitions
CSS transitions create smooth animations between property values. When a property changes (e.g., on hover), transition makes the change animate over a specified duration instead of happening instantly. Use transition-property to specify what changes, transition-duration for how long, and transition-timing-function for the animation curve. Transitions are ideal for UI feedback, hover effects, and simple state changes.
Transition properties
Property | Purpose | Example |
|---|---|---|
| Which property to animate | background-color, transform |
| How long animation lasts | 0.3s, 500ms |
| Animation curve | ease, ease-in-out, linear |
| Wait before starting | 0.1s, 200ms |
| Shorthand | all 0.3s ease 0.1s |
/* Longhand */
.button {
background-color: blue;
transition-property: background-color;
transition-duration: 0.3s;
transition-timing-function: ease;
transition-delay: 0s;
}
.button:hover {
background-color: darkblue; /* animates over 0.3s */
}
/* Shorthand: property duration timing delay */
.button {
background-color: blue;
transition: background-color 0.3s ease 0s;
}
/* Animate all properties */
.box {
width: 100px;
height: 100px;
background: blue;
transition: all 0.5s ease; /* all properties animate */
}
.box:hover {
width: 200px;
height: 200px;
background: red; /* all three properties animate */
}
/* Multiple properties */
.element {
transition:
background-color 0.3s ease,
color 0.3s ease,
transform 0.3s ease;
/* Different properties can have different durations */
}Timing functions
Function | Behavior | Best for |
|---|---|---|
| Slow start and end, fast middle (default) | General animations |
| Constant speed throughout | Continuous motion |
| Slow start, fast end | Items disappearing |
| Fast start, slow end | Items appearing |
| Slow start and end, fastest middle | Bouncy feel |
| Custom curve | Precise control |
/* Timing function examples */
.ease {
transition: all 1s ease; /* slow, fast, slow */
}
.linear {
transition: all 1s linear; /* constant speed */
}
.ease-in {
transition: all 1s ease-in; /* slow start */
}
.ease-out {
transition: all 1s ease-out; /* slow end */
}
.ease-in-out {
transition: all 1s ease-in-out; /* slow both ends */
}
/* Custom bezier curve */
.custom {
transition: all 1s cubic-bezier(0.17, 0.67, 0.83, 0.67);
/* (x1, y1, x2, y2) control points */
}
/* Steps for discrete animation */
.steps {
transition: all 1s steps(10); /* animates in 10 discrete steps */
}
/* Common patterns */
.fade-in {
opacity: 0;
transition: opacity 0.3s ease-out;
}
.fade-in.visible {
opacity: 1;
}
.slide-in {
transform: translateX(-100%);
transition: transform 0.5s ease-out;
}
.slide-in.visible {
transform: translateX(0);
}Practical transition examples
<!-- Button with smooth feedback -->
<button class="btn">Click me</button>
.btn {
background: #0066cc;
color: white;
border: none;
padding: 10px 20px;
border-radius: 4px;
cursor: pointer;
transition: all 0.3s ease;
}
.btn:hover {
background: #0052a3;
transform: translateY(-2px);
box-shadow: 0 4px 12px rgba(0, 102, 204, 0.4);
}
.btn:active {
transform: translateY(0);
box-shadow: 0 2px 4px rgba(0, 102, 204, 0.2);
}
<!-- Link with color transition -->
<a href="#" class="link">Link text</a>
.link {
color: #0066cc;
text-decoration: none;
border-bottom: 2px solid transparent;
transition: all 0.3s ease;
padding-bottom: 2px;
}
.link:hover {
color: #0052a3;
border-bottom-color: #0052a3;
}
<!-- Card lift on hover -->
<div class="card">Content</div>
.card {
background: white;
border-radius: 8px;
padding: 20px;
box-shadow: 0 2px 8px rgba(0,0,0,0.1);
transition: all 0.3s ease;
}
.card:hover {
box-shadow: 0 12px 24px rgba(0,0,0,0.15);
transform: translateY(-8px);
}
<!-- Smooth visibility toggle -->
.modal {
opacity: 0;
visibility: hidden;
transform: scale(0.9);
transition: all 0.3s ease;
}
.modal.active {
opacity: 1;
visibility: visible;
transform: scale(1);
}Transitioning complex properties
/* Colors transition smoothly */
.element {
background-color: blue;
transition: background-color 0.3s ease;
}
.element:hover {
background-color: red; /* smoothly interpolates */
}
/* Transforms transition */
.element {
transition: transform 0.3s ease;
}
.element:hover {
transform: rotate(45deg) scale(1.2);
}
/* Box-shadow transitions */
.element {
box-shadow: 0 2px 4px rgba(0,0,0,0.1);
transition: box-shadow 0.3s ease;
}
.element:hover {
box-shadow: 0 10px 25px rgba(0,0,0,0.2);
}
/* Multiple color properties */
.element {
background: white;
color: black;
border: 1px solid #ccc;
transition: background 0.3s, color 0.3s, border-color 0.3s;
}
.element:hover {
background: #333;
color: white;
border-color: white;
}
/* Width/height with caution (can be slow) */
.element {
width: 100px;
height: 100px;
transition: width 0.3s, height 0.3s; /* slower, triggers layout */
}
.element:hover {
width: 200px;
height: 200px;
}
/* Better: use transform instead */
.element {
transition: transform 0.3s; /* faster, GPU-accelerated */
}
.element:hover {
transform: scale(2);
}Preventing transitions
/* Disable transitions globally */
* {
transition: none;
}
/* Disable specific property */
.element {
transition: all 0.3s ease;
}
.element.no-animate {
transition: none; /* overrides previous */
}
/* Transition none removes all transitions */
.element {
transition: none; /* turns off all transitions */
}
/* Force immediate change */
.element.instant {
transition-duration: 0s; /* changes instantly */
}
/* Disable on certain elements */
@media (prefers-reduced-motion: reduce) {
* {
transition-duration: 0.01ms !important;
animation-duration: 0.01ms !important;
}
}