Shadows are one of the most impactful tools in a designer's toolkit. They create depth, establish hierarchy, and make interfaces feel tactile and real. The CSS box-shadow property lets you add shadows to any HTML element — from subtle card elevations to dramatic glow effects. In this guide, we'll cover the complete syntax, walk through real-world examples, and show you how to use a box shadow generator to create professional shadow effects quickly.
box-shadow
The box-shadow property attaches one or more shadows to an element. It doesn't affect layout — shadows are purely visual and don't take up space. The browser renders them outside (or inside, with inset) the element's border box.
inset
box-shadow: [inset] offsetX offsetY blurRadius spreadRadius color;
Here's what each value controls:
rgba()
The minimum required values are offsetX, offsetY, and color. Blur and spread default to 0 if omitted.
The most common shadow for card-based UIs. Creates a gentle lift effect.
box-shadow: 0 4px 6px -1px rgba(0, 0, 0, 0.3), 0 2px 4px -2px rgba(0, 0, 0, 0.2);
No blur, creates a bold, flat-design aesthetic popular in modern illustrations.
box-shadow: 4px 4px 0 #6366f1;
Places the shadow inside the element for a pressed-in or recessed look.
box-shadow: inset 0 2px 8px rgba(0, 0, 0, 0.5);
Dual shadows (light and dark) create a soft, extruded plastic appearance.
box-shadow: 8px 8px 16px #0a0f1e, -8px -8px 16px #1a2540;
Large blur radius with a vibrant color creates a glowing effect.
box-shadow: 0 0 20px rgba(99, 102, 241, 0.5), 0 0 40px rgba(99, 102, 241, 0.2);
You can stack multiple shadows by separating them with commas. This technique is used to create more realistic, complex shadow effects.
/* Realistic elevation */ box-shadow: 0 1px 2px rgba(0, 0, 0, 0.07), 0 2px 4px rgba(0, 0, 0, 0.07), 0 4px 8px rgba(0, 0, 0, 0.07), 0 8px 16px rgba(0, 0, 0, 0.07), 0 16px 32px rgba(0, 0, 0, 0.07); /* Colored glow + elevation */ box-shadow: 0 4px 6px rgba(0, 0, 0, 0.3), 0 0 15px rgba(99, 102, 241, 0.3);
The key to realistic multi-layer shadows is using progressively larger offsets and blurs with decreasing opacity. This mimics how real light sources create shadows at multiple distances.
Inset shadows are perfect for creating recessed UI elements like input fields, wells, and indented areas.
/* Input field feel */ .input-shadow { box-shadow: inset 0 1px 3px rgba(0, 0, 0, 0.3); } /* Top light source (recessed surface) */ .inset-top { box-shadow: inset 0 2px 4px rgba(0, 0, 0, 0.3), inset 0 -1px 1px rgba(255, 255, 255, 0.05); } /* Combine inset + outset for a framed look */ .frame-shadow { box-shadow: inset 0 0 0 1px rgba(255, 255, 255, 0.1), 0 4px 12px rgba(0, 0, 0, 0.3); }
CSS offers two shadow approaches, and they behave differently:
filter: drop-shadow()
/* box-shadow - rectangular */ .card { box-shadow: 0 4px 12px rgba(0,0,0,0.3); } /* drop-shadow - follows shape */ .logo { filter: drop-shadow(0 4px 8px rgba(0,0,0,0.3)); }
If your element has transparent areas and you want the shadow to follow the visible shape, use drop-shadow. For everything else, box-shadow is the standard choice.
drop-shadow
Box shadows are generally performant, but keep these tips in mind:
transform: translateY()
will-change: box-shadow
.card { border-radius: 12px; box-shadow: 0 1px 3px rgba(0,0,0,0.12), 0 1px 2px rgba(0,0,0,0.24); transition: box-shadow 0.3s ease; } .card:hover { box-shadow: 0 10px 20px rgba(0,0,0,0.15), 0 3px 6px rgba(0,0,0,0.10); }
.btn { box-shadow: 0 2px 4px rgba(0,0,0,0.2); } .btn:active { box-shadow: 0 1px 2px rgba(0,0,0,0.2); transform: translateY(1px); }
In dark mode, shadows need to be more subtle since they blend with dark backgrounds:
/* Light mode */ --shadow: 0 1px 3px rgba(0, 0, 0, 0.12); /* Dark mode - use lighter shadow or glow */ --shadow: 0 1px 3px rgba(0, 0, 0, 0.5); --shadow-glow: 0 0 0 1px rgba(255, 255, 255, 0.05);
Use the box-shadow property: box-shadow: 5px 5px 10px rgba(0,0,0,0.3);. The four values are: horizontal offset, vertical offset, blur radius, and color. Positive offsets move the shadow right/down, negative values move it left/up. A larger blur radius creates a softer shadow.
box-shadow: 5px 5px 10px rgba(0,0,0,0.3);
box-shadow creates a shadow of the element's rectangular box, even if the element has transparent areas. drop-shadow (applied via the filter property) follows the actual shape of the element, including transparent areas. Use box-shadow for rectangular elements and drop-shadow for PNG images, SVG elements, or shapes with irregular outlines.
filter
Add the inset keyword to the box-shadow property: box-shadow: inset 0 2px 4px rgba(0,0,0,0.3);. This places the shadow inside the element, creating a recessed or pressed-in appearance. You can combine inset and outset shadows by listing multiple shadow values separated by commas.
box-shadow: inset 0 2px 4px rgba(0,0,0,0.3);
By default, box-shadow automatically follows the border-radius of an element. If your element has border-radius: 16px, the shadow will also have rounded corners matching that radius. This is one of the key advantages of box-shadow over older techniques like using a background image for shadows.
border-radius: 16px
🖱️ Design shadows visually. Try our free Box Shadow Generator — drag sliders, layer shadows, copy CSS instantly.
Visual shadow designer with layers
Create rounded corners for elements
Build beautiful gradient backgrounds