CSS UTILITY

CSS Box Shadow Generator

Design complex multi-layered box shadows with real-time preview. Adjust offsets, blur, spread, color, and inset to create production-ready CSS.

4px
4px
10px
0px
25%
#000000
Generated CSS
box-shadow: 4px 4px 10px 0px rgba(0,0,0,0.25);

The Science of Digital Depth

Material Elevation

In Material Design, elevation determines the visual hierarchy of elements. A card at elevation 1 uses a soft shadow like box-shadow: 0 1px 3px rgba(0,0,0,0.12), 0 1px 2px rgba(0,0,0,0.24), while a modal dialog at elevation 24 needs a much larger shadow with 15-24px blur. The key insight: real shadows are never a single layer. Google's own elevation system uses two shadows per level — a key light (sharp, directional) and an ambient light (soft, diffused) — to create realistic depth on a flat screen.

The Syntax Decoded

box-shadow: [inset] <x> <y> <blur> <spread> <color>

X/Y offset controls the shadow direction, simulating a light source. Positive X moves the shadow right, positive Y moves it down. Blur radius(always positive) determines softness — a 0px blur creates a razor-sharp copy of the shape, while 20px produces a soft ambient glow. Spreadexpands (positive) or contracts (negative) the shadow from the element's edge. A spread of -5px combined with a blur of 10px creates a shadow smaller than the element, perfect for floating effects.

Neumorphism — The Soft UI Technique

Neumorphism creates a “soft extrusion” effect using two box-shadow layers on a background-colored element: one light shadow (top-left) and one dark shadow (bottom-right). A typical neumorphic card on a #e0e0e0 background uses box-shadow: 8px 8px 16px #bebebe, -8px -8px 16px #ffffff. For pressed states, add the insetkeyword to both shadows. While visually striking, neumorphism has accessibility trade-offs — low contrast between elements can make interfaces harder to navigate, so use it selectively on decorative or non-critical components.

Performance & Rendering

Box shadows are rendered on the CPU during the paint phase, not composited on the GPU like transforms and opacity. A single shadow with a 10px blur on a 200px element is negligible, but stacking 5+ layers with 50px+ blur on dozens of elements can cause visible jank during scroll. For smooth animations, prefer filter: drop-shadow()which is GPU-composited, or animate a pseudo-element's opacity with the shadow pre-applied. On mobile devices, keep blur radii under 20px and limit shadow layers to 2-3 per element.

Frequently Asked Questions

What is the difference between box-shadow and filter: drop-shadow()?

box-shadow always renders as a rectangle (following the border-box), even on elements with border-radius or clip-path. filter: drop-shadow() traces the actual visible alpha channel of the element, including transparent PNG regions and CSS clip paths. Use box-shadow for standard card elevation, and drop-shadow for irregularly shaped elements like SVG icons or clipped images.

How do I create a shadow on only one side of an element?

Use a negative spread value equal to the blur radius, then offset in the desired direction. For example, a bottom-only shadow: box-shadow: 0 8px 8px -8px rgba(0,0,0,0.3). The negative spread contracts the shadow inward by 8px on all sides, then the 8px Y-offset pushes it below the element, making it visible only at the bottom edge.

Can I animate box-shadow on hover without performance issues?

Directly transitioning box-shadow triggers a repaint on every frame, which can be expensive. A better pattern: apply the final shadow to a ::afterpseudo-element positioned behind the element, then animate only the pseudo-element's opacity on hover. This way, the browser only composites opacity (GPU-accelerated) rather than recalculating shadow geometry every frame.