Learn how to use SVG masks in CSS to create complex, non-rectangular shapes and transparent cutouts for images or elements.
What it is
CSS masking allows you to control the visibility of an element using a mask image. When combined with SVG (Scalable Vector Graphics), this technique enables precise, scalable, and complex shape definitions that go beyond simple rectangles or circles. The mask determines which parts of the target element are visible based on the alpha channel or luminance of the mask source. In the context of SVG masks, you define a <mask> element within an inline SVG block, and then reference it via the CSS mask property.
Related terms: Alpha channel, Luminance mask, Inline SVG, Clip-path (a related but distinct concept).
Why it matters
- Complex Shapes: Enables organic, irregular, or intricate designs without needing pre-rendered PNGs with transparency.
- Scalability: Since SVG is vector-based, masks remain sharp at any resolution or zoom level.
- Performance: Reduces HTTP requests by embedding mask definitions directly in HTML/CSS rather than loading external image files.
- Dynamic Control: Masks can be animated or modified via JavaScript more easily than raster images.
Syntax or steps
- Create an inline
<svg>element in your HTML. - Inside the SVG, define a
<mask>element with a unique ID. - Within the mask, draw white shapes where content should be visible and black shapes where it should be hidden (for luminance masks) or use opacity/alpha values.
- In your CSS, apply the mask to an element using
mask: url('#id');. - Ensure the masked element has a background or content to reveal.
Example
<!-- HTML Structure -->
<svg width="0" height="0">
<defs>
<mask id="circle-cutout" maskUnits="objectBoundingBox" maskContentUnits="objectBoundingBox">
<!-- White rectangle makes everything visible initially -->
<rect x="0" y="0" width="1" height="1" fill="white" />
<!-- Black circle hides the center -->
<circle cx="0.5" cy="0.5" r="0.3" fill="black" />
</mask>
</defs>
</svg>
<div class="masked-box"></div>
<style>
.masked-box {
width: 200px;
height: 200px;
background-color: #3498db;
/* Apply the SVG mask */
mask: url(#circle-cutout);
-webkit-mask: url(#circle-cutout); /* For older WebKit browsers */
}
</style>
Explanation: The SVG defines a mask where a full white rectangle ensures the base visibility, while a black circle subtracts from that visibility, creating a "donut" hole effect. The CSS applies this mask to a blue square div. Note the use of objectBoundingBox units, which allow the mask to scale relative to the element's size.
Common mistakes
- Missing Vendor Prefixes: Older browsers require
-webkit-mask. Always include both properties for broader compatibility. - Incorrect Mask Units: Using
userSpaceOnUseinstead ofobjectBoundingBoxcan cause the mask to not scale with the element if coordinates are absolute. - SVG Visibility: If the SVG containing the mask definition is set to
display: none, some browsers may fail to render the mask. Usewidth="0" height="0"instead. - Confusing Mask with Clip-Path:
clip-pathcuts off geometry entirely;maskcontrols transparency. Do not expect partial transparency from a clip-path.
When to use it
| Feature | CSS Masking (SVG) | CSS Clip-Path |
|---|---|---|
| Transparency | Supports partial transparency (grayscale/alpha) | Binary (visible or hidden) |
| Complexity | High (supports gradients, patterns, text) | Moderate (shapes, polygons) |
| Best For | Fades, soft edges, textured overlays | Hard geometric cuts, responsive shapes |
Practice
Guided Exercise: Modify the example above to create a star-shaped mask. Replace the <circle> with a <polygon> defining a star path, filled with black.
Challenge: Create a gradient mask that fades out the bottom half of an image. Hint: Use a <linearGradient> inside the mask definition applied to a rectangle.
Quick check
Q: What color value in an SVG mask typically represents fully opaque content?
A: White (or high luminance). Black represents fully transparent content.
Summary
SVG masking provides powerful control over element visibility through scalable vector definitions. By leveraging luminance or alpha channels within inline SVGs, developers can achieve complex visual effects that are both performant and responsive.