Creating Symbol-Based SVG Sprites
Learn how SVG <symbol> elements work and how they form the foundation of modern SVG sprite sheets. Understand id attributes, viewBox, and the relationship between symbol and use.
Detailed Explanation
Creating Symbol-Based SVG Sprites
The <symbol> element is the building block of SVG sprites. It defines a reusable graphic that is not rendered directly but can be instantiated anywhere with <use>. This is different from older approaches that used <defs> with <g> elements or CSS background positioning on a single sprite image.
How <symbol> Works
A <symbol> defines a graphical template with its own viewBox and coordinate system. It lives inside an <svg> container but produces no visual output on its own:
<svg xmlns="http://www.w3.org/2000/svg" style="display:none">
<symbol id="icon-star" viewBox="0 0 24 24">
<path d="M12 2l3.09 6.26L22 9.27l-5 4.87
1.18 6.88L12 17.77l-6.18 3.25L7
14.14 2 9.27l6.91-1.01L12 2z"/>
</symbol>
<symbol id="icon-heart" viewBox="0 0 24 24">
<path d="M20.84 4.61a5.5 5.5 0 0 0-7.78 0L12
5.67l-1.06-1.06a5.5 5.5 0 0 0-7.78
7.78l1.06 1.06L12 21.23l7.78-7.78
1.06-1.06a5.5 5.5 0 0 0 0-7.78z"/>
</symbol>
</svg>
The id Attribute
Every symbol needs a unique id. This is the reference you use in <use href="#id">. A good naming convention is icon-{name} to avoid conflicts with other IDs in your HTML. Keep IDs lowercase with hyphens for consistency.
The viewBox Attribute
Each <symbol> can have its own viewBox, which defines the coordinate system for the paths inside it. This means you can combine icons from different sources with different viewBoxes (e.g., 0 0 24 24, 0 0 16 16, 0 0 512 512) and they will all scale correctly when referenced.
Referencing Symbols with <use>
To render a symbol, use the <use> element inside an <svg>:
<svg width="24" height="24">
<use href="#icon-star"/>
</svg>
<svg width="48" height="48" class="text-red-500">
<use href="#icon-heart"/>
</svg>
The <use> element creates a deep clone of the referenced symbol. The outer <svg> controls the rendered size, while the symbol's viewBox handles the internal scaling.
Why Not <defs> + <g>?
The older pattern of wrapping icons in <defs><g id="icon"> works but has a key limitation: <g> does not support its own viewBox. You would need to set the viewBox on the outer <svg> container or manage scaling manually. <symbol> was specifically designed for this use case and is the recommended approach.
Use Case
Front-end developers creating SVG sprite sheets from scratch, designers preparing icon exports for development teams, and anyone learning the SVG specification for icon management.