apike.ca

We need more traffic. Please use the social buttons above to spread the word!

SVG Tutorial

SVG Matrix Transformations

When you draw in SVG, matrix math is used to figure out where on the screen the point is. Consider a document with a view box which is 200 by 200 pixels but on a display which is 100 by 100 pixels. A point at (20, 20) must be drawn at (10, 10) on the display. This transformation occurs for each and every point. The SVG viewer does this work for you using matrix math.

Matrix math makes many types of transformations very easy to do. Matrix math however can't do vector field transformations like warps, swirls or bends. The SVG specification has a very good explanation on how the matrix math works. SVG allows you to add transformations using matrix math to elements before it decides where the points are on the display. The transformation live demo allows you to play with these and see the result visually.

Code
Result
1
2
3
4
5
<g transform="scale(5) translate(15, 15) rotate(20) skewX(20) skewY(5)">
  <rect x="10" y="10" width="5" height="5" fill="firebrick" />
  <circle r="10" fill="seagreen" stroke="blue"/>
  <rect x="5" y="5" width="12" height="2" fill="gray" stroke="silver"/>
</g>

The following pseudo-functions are white space separated and applied in the order written. Transform functions are put in the 'transform' attribute of any container element ('g', 'svg', 'image') or any shape. Patterns and gradients have attributes which also accept transformations.

Function List

Translate

translate(x, y)
Code 1. Translate to (x, y). 'y' is optional.

Move the points in the object by (x, y). If 'y' is not set then it is assumed to be 0. The translate transformation is so fundamental that attributes like 'x' and 'y' are built into elements like 'rect' as well. The two ways to offset an element are equivalent. Indeed, if you are using transformations, you will need to consider that offset attributes are converted into a transformation that may affect transformations that you add.

Scale

scale(sx, sy)
Code 2. Scale by sx on the x-axis and sy on the y-axis. sy is optional.

Scale the points along the x and y axis. If sy is not used then both x and y axis are scaled by sx.

Rotate

rotate(angle, cx, cy)
Code 3. Rotate around cx and cy. cx and cy are optional. The angle is in degrees.

Rotate the points around the point (cx, cy). This point is an offset of the current view box. If cx and cy are not present then the points are rotated around the origin.

Skew

skewX(angle)
Code 4. Skew along the x-axis. The angle is in degrees.
skewY(angle)
Code 5. Skew along the y-axis. The angle is in degrees.

These skew along the axis determined by the function used. The distance "skewed" is the tan of the angle.

Matrix

matrix(a, b, c, d, e, f)
Code 6. Input a transformation matrix directly.

This directly multiplies a transformation matrix against the current transformation matrix. The other functions are much easier to understand and much easier to maintain and manipulate.

Transformation Array
Image 1. How the transformation matrix is constructed.

Order of Operation and Nesting

With matrix math, the order you do transformations is important. Translating and then rotating gives a different result from rotating and then translating. Transformations can also be nested. This is illustrated below. The final result in green is not in the same position even though the exact same transformations were used.

Example 2. The left side's green square is translated and then rotated. The right is the reverse order. (Download)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
<!-- Translate then rotate -->
 
<use xlink:href="#example" fill="red" />
<g transform="translate(15, 15)" fill="yellow">
    <use xlink:href="#example" />
    <g transform="rotate(30)" fill="green">
        <use xlink:href="#example" />
    </g>
</g>
 
<!-- Rotate then translate -->
 
<g transform="translate(65)">
<use xlink:href="#example" fill="red" />
<g transform="rotate(30)" fill="yellow">
    <use xlink:href="#example" />
    <g transform="translate(15, 15)" fill="green">
        <use xlink:href="#example" />
    </g>
</g>
</g>
Code 1. The previous example's code.
Related Topics