Overview
Card hover-lift effect that combines transform: translateY with an expanding box-shadow radius so the card visibly rises from the surface. Three product contexts ship: dashboard metric tile, product-catalogue card with thumbnail, hero CTA panel with arrow.
When to use it
Reach for hover-lift on linkable cards (product grids, dashboard tiles, blog index entries). Skip it for dense list rows — the cumulative translateY noise becomes distracting. Skip it for touch-first contexts; without hover, the lift never reads, so save the design budget for touch-feedback patterns instead.
How it works
At rest the card has a tight box-shadow: 0 2px 4px rgba(0,0,0,0.08) suggesting it sits close to the surface. On :hover, transition to a wider, softer shadow like 0 12px 28px rgba(0,0,0,0.16) alongside a transform: translateY(-4px). The compound effect — shadow growing + element rising — sells the physics. Use a transition duration around 180–240ms with cubic-bezier(.2, .8, .2, 1) for the lift to feel material rather than abrupt. Always also handle :focus-visible with the same lift so keyboard users see the affordance.
Production gotchas
Animating box-shadow is more expensive than animating transform — both trigger paint on the shadow region. For high card counts, swap to a pre-baked dual-shadow approach: layer two box-shadows with different opacities and animate the second layer’s opacity instead of the radii. The translate must not push the card outside any clipping ancestor — check overflow: hidden parents. On macOS, the soft-shadow rendering treats blurs above ~30px as expensive on retina displays.
Accessibility
Cards used as links must be a real <a> element — not a div with onClick — so keyboard users can tab to them. The hover-lift must mirror under :focus-visible or you orphan keyboard users from the affordance. Under prefers-reduced-motion: reduce drop the translate and keep only the shadow change, or drop the animation entirely and use a subtle border change for the focused state.
References