Scalable Vector Graphics
SVG(Scalable Vector Graphics) are great for using on the web, not only they are scalable and deliver high quality on any screen resolution, they are also code based, which means we can embed and edit a SVG file just like HTML elements.
Exporting SVGs
We can create SVG files by writing the code in our HTML. This would work well for simpler shapes, for more complex shapes in our SVG we can use software like Adobe Illustrator, Inkscape, or Sketch and export the file, to then use in one of the ways described in next section.
Using SVGs
We can use SVG files as images and embed them in our HTML using <img>
tag or background
property in CSS or we can embed the SVG code directly in our HTML document.
Embedding the SVG code in our HTML will allow us to access the editing capabilities for an SVG or to add interactivity.
Creating SVGs
For creating a SVG file we can simply create a new file in VS Code and save it with .svg
extension and write the code in it. In this case we can use img
tag or background
property to display the .svg
file on our HTML page.
For inline SVG we can write the SVG code into the HTML of the page to create the graphic directly on the page.
The SVG Element
Weather we create a separate file or use inline SVG code we need to start with the <svg></svg>
element, which is the container element for the svg graphic.
We can add different attributes to this element like version
, xmlns
, width
, height
, preserveAspectRatio
, and viewBox
to define the canvas of the SVG graphic.
For a .svg
file we will write the following element:
<svg version="1.1" xmlns="http://www.w3.org/2000/svg">
<!-- SVG graphic code here -->
</svg>
For inline SVG code added directly to the HTML the version
and xmlns
attributes can be left out
<svg>
<!-- SVG graphic code here -->
</svg>
Viewport and viewBox
The viewport of SVG is defined by the width
and height
attribute values, we can also think of it as the area of an SVG that is visible. The SVG below has a viewport of 200x300.
<svg width="200" height="300">
<!-- SVG graphic code here -->
</svg>
viewBox
is the attribute that defines the area in the SVG in which the graphics will stretch to fit. We can use four values for the viewBox
attribute min-x
, min-y
, width
, and height
. The SVG below has viewport of 200x300 and the viewBox
that starts at the 0 x
and 0 y
coordinates with the same width
and height
as the viewport.
<svg width="200" height="300" viewBox="0 0 200 300">
<!-- SVG graphic code here -->
</svg>
Note
There can be more content in an SVG out of its viewport. This is a common practice while creating SVG Sprites.
Basic Shapes
For adding different shapes to our SVG graphics we need to use different tags.
<rect/>
This element generates a rectangle and will require the following attributes width
and height
.
<rect/>
is a self closing element and since we are writing XML we will need to close the singular element with a /
at the end of the element.
We can add more information using the following attributes
fill
for the fill colour (default black)x
for x-axis coordinatey
for y-axis coordinaterx
for rounded corners with x-axisry
for rounded corners with y-axis
<svg width="200" height="100" viewBox="0 0 200 100">
<rect width="200" height="100" fill="#CFBEE1" rx="10" ry="10"/>
</svg>
<circle/>
<circle/>
element is used to add a circle with the required x coordinate cx
, y coordinate cy
and radius r
. We can also use the fill
attribute for defining the fill colour.
<svg width="100" height="100" viewBox="0 0 100 100">
<circle cx="50" cy="50" r="50" fill="#BBF7A2"/>
</svg>
<ellipse/>
<ellipse/>
element is used to add an ellipse with the required x coordinate cx
, y coordinate cy
and two radii rx
for horizontal and ry
for vertical. We can also use the fill
attribute for defining the fill colour.
<svg width="300" height="50" viewBox="0 0 300 50">
<ellipse cx="150" cy="25" rx="150" ry="25" fill="#F388E8"/>
</svg>
<line/>
The <line/>
element is used to create a straight line by defining the x and y coordinates for the starting and ending points. Using x1
and y1
attributes for the starting point and x2
and y2
for the ending point coordinates.
The stroke-width
is used to define the thickness of the line and stroke
attribute is to add the colour of the line.
<svg width="140" height="64" viewBox="0 0 140 64">
<line x1="4" y1="4" x2="140" y2="60" stroke="#818ccf" stroke-width="4"/>
</svg>
<polyline/>
The <polyline/>
is used to create an open shape with connected straight lines, using the points
attribute we can specify x and y coordinates for the lines.
The x and y points are presented in groups separated by commas x,y
followed by a space and the next x,y
group
We can also use stroke
attribute for the colour of the line, fill
for the colour of the inside containing area, and stroke-width
for the thickness of the line
<svg width="20" height="50" viewBox="0 0 20 50">
<polyline points="10,10 10,50" fill="white" stroke="#ef898b" stroke-width="6"/>
</svg>
The code above will create a single 6px thick vertical line starting at 10px x coordinate and 10px y coordinate and going to 10px x coordinate and 50px y coordinate or 40px in length
Adding on to the above code, we can define the next x
,y
group for the next point in this polyline
<svg width="50" height="50" viewBox="0 0 50 50">
<polyline points="10,10 10,50 50,50" fill="white" stroke="#ef898b" stroke-width="6"/>
</svg>
And more points
<svg width="110" height="160" viewBox="0 0 110 160">
<polyline points="10,10 10,50 50,50, 50,100 100,100 100,150" fill="white" stroke="#ef898b" stroke-width="6"/>
</svg>
<polygon />
The <polygon/>
element is quite similar to polyline, a polygon is used to create a closed shape with lines. We define different points using the points
attribute and use fill
attribute for the colour of the contained area between the lines.
<svg width="60" height="60" viewBox="0 0 60 60">
<polygon points="0,20 20,20 30,0 40,20 60,20 40,35 60,60 30,45 0,60 20,35 " fill="#b6e2ff"/>
</svg>
Styling the SVG
Since SVG is comprised of elements, we can use our CSS file to style these tags. We can also add class
and id
attributes to different elements in our svg and use them as selectors.
<svg width="60" height="145" viewBox="0 0 60 145" class="ferry-wand">
<polygon class="star" points="0,20 20,20 30,0 40,20 60,20 40,35 60,60 30,45 0,60 20,35 " fill="#b6e2ff"/>
<line class="stick" x1="30" y1="35" x2="30" y2="145" stroke="#818ccf" stroke-width="4"/>
</svg>
Stacking Order
The stacking order of our shapes in an SVG is based on the order in which they are added to the svg
element, the order cannot be changed by using z-index
Grouping
When working with an SVG that has different shapes we can group them together using the <g></g>
element. Grouping allows us to animate and style the group of elements together.
<svg width="60" height="145" viewBox="0 0 60 145" class="ferry-wand">
<line x1="30" y1="35" x2="30" y2="145" stroke="#818ccf" stroke-width="4"/>
<polygon class="star" points="0,20 20,20 30,0 40,20 60,20 40,35 60,60 30,45 0,60 20,35 " fill="#b6e2ff"/>
<g class="magic">
<circle class="bubble" cx="4" cy="30" r="4" fill="#ED6E46" />
<circle class="bubble" cx="30" cy="4" r="4" fill="#ED6E46" />
<circle class="bubble" cx="56" cy="30" r="4" fill="#ED6E46" />
<circle class="bubble" cx="30" cy="56" r="4" fill="#ED6E46" />
</g>
</svg>
Reusing Groups
We can add an id to the <g></g>
element and then add the <use/>
element to reuse the group in our SVG.
The <use/>
element has xlink:href
attribute which uses the id value of the <g></g>
element. We can also add the x
attribute for x coordinates, y
attribute for y coordinates, width
and height
attributes to the <use/>
element.
<svg width="60" height="60" viewBox="0 0 60 60">
<g id="bubbles">
<circle class="bubble" cx="4" cy="30" r="4" fill="#ED6E46" />
<circle class="bubble" cx="30" cy="4" r="4" fill="#ED6E46" />
<circle class="bubble" cx="56" cy="30" r="4" fill="#ED6E46" />
<circle class="bubble" cx="30" cy="56" r="4" fill="#ED6E46" />
</g>
<use xlink:href="#bubbles" class="dup-bubbles" />
</svg>
defs Element
Following along the concept of reusing the elements in our SVG we can use the <defs></defs>
element to define a graphic.
The graphics defined in the <defs></defs>
element will not be rendered on the page until it is added to the page with the <use/>
element.
<svg width="300" height="200" viewBox="0 0 300 200">
<defs>
<rect id="brick" width="200" height="100" fill="#CFBEE1"/>
<circle id="ball" r="50" fill="#8CC9BB"/>
</defs>
<use xlink:href="#brick"/>
<use xlink:href="#ball" x="200" y="50"/>
<use xlink:href="#brick" x="50" y="100"/>
<use xlink:href="#ball" x="50" y="150"/>
</svg>
<text>
Element
The text element allows us to add text to our SVG graphics. We can style the text using CSS font properties and some advanced effects.
The best part is that even if the text is in a graphic it is still accessible which is not the case if we add text to a .jpeg or .png file.
<svg width="300" height="100" viewBox="0 0 300 100">
<text x="0" y="100" fill="tomato">PIZZA</text>
</svg>
Gradient
One of the advance effects we can use on the text in an SVG is gradient.
For applying a gradient on text we first have to define a gradient, using the <linearGradient></linearGradient>
element and the <stop/>
elements.
Inside the <stop/>
element we can add the stop-color
attribute for defining the stop colour and add offset
attribute with percentage value to set where the defined colour should be added.
<svg>
<defs>
<linearGradient id="mygradient">
<stop offset="0%" stop-color="#9ebb8f"/>
<stop offset="100%" stop-color="#86f2ed"/>
</linearGradient>
</defs>
</svg>
Once we have the gradient defined we can now use it as a fill on any element by simply using the id
of the gradient as value of the fill
for an element
<svg width="250" height="100" viewBox="0 0 250 100">
<defs>
<linearGradient id="mygradient">
<stop offset="0%" stop-color="#ff69eb"/>
<stop offset="100%" stop-color="#ffdc5e"/>
</linearGradient>
</defs>
<rect width="100" height="100" fill="url(#mygradient)"/>
<text x="100" y="50" fill="url(#mygradient)" font-size="2rem">Colourful</text>
</svg>
Patterns
The <pattern></pattern>
element in SVG can be used to create repeating patterns out of shapes or images to be used as fill
value in other elements. We use the id
of the pattern as the value.
We can specify the referencing coordinates for x
,y
,width
and height
in our pattern and patternUnits
attribute with a value of userSpaceOnUse
is added to allow the pattern, reference the element on which it is used.
<svg width="600" height="220" viewBox="0 0 600 220">
<defs>
<pattern id="dots" x="10" y="10" width="10" height="10" patternUnits="userSpaceOnUse">
<circle cx="5" cy="5" r="5" fill="#e59e91" />
</pattern>
</defs>
<rect x="10" y="10" width="200" height="200" fill="url(#dots)" />
<text x="210" y="210" fill="url(#dots)" font-size="8rem">DOTS</text>
</svg>
We can also use an image as a pattern, for this we need to use the <image/>
element inside the <pattern></pattern>
element
<svg width="600" height="220" viewBox="0 0 600 220">
<defs>
<pattern width="300" height="300" id="pizza" patternUnits="userSpaceOnUse">
<image width="300" xlink:href="/images/svg-mask-pizza.jpg"/>
</pattern>
</defs>
<text x="0" y="100" fill="url(#pizza)" style="font-size:6rem;font-weight:bold;">PIZZA</text>
</svg>