Mark Allen Neil photo

Mark Allen Neil.com

An online résumé, blog, biography and digital sandbox

Articles

An introduction to SVG (scalable vector graphics)

Posted 2009-10-19 in Web

SVG - Scalable Vector Graphics

SVG is a language for describing two-dimensional graphics and graphical applications in XML. Scalable graphics have a few advantages over bit-mapped images… i.e. most image files you’ll find anywhere. Two big advantages which have been useful for me are…

  • The human readable, textual nature of the language allows one to describe complex geometries programmatically.
  • SVG drawings are scalable and therefore resolution independent, so images can be zoomed to arbitrary extent without loss (no jagged edges).

How I came to use SVG

I “discovered” SVG while doing a project for a client in 2008… I needed to be able to create images of solar cells in a flexible and resolution independent way. I’m a big fan of XML, where data is highly organized and self describing… so SVG was a perfect fit for my needs as it is a dialect of XML. I’ll explore the particular application of SVG to solve a client’s problems in future article.

Note that this article isn’t really a proper introduction to SVG… it is more a “look, here’s a cool way to draw pictures.” I’ve found SVG to be very underused and think more folks should try it out. There are a few resources out there to really get you started with SVG… check out SVG Specifications, SVG Wiki and SVG Tutorial.

A simple SVG drawing

The following is a simple SVG drawing of a green circle inside of blue rectangle… followed by the SVG source for the drawing (granted the image is a bit underwhelming). Now use CTRL+ to zoom your browser window several times and notice that the edge of the green circle remains “smooth.” This is an example of the scalable nature of SVG… a vector image can be scaled to arbitrary extents without loss.

Simple SVG drawing

Corresponding SVG source

<svg xmlns="http://www.w3.org/2000/svg" version="1.1">
  <rect x="0" y="0" width="250" height="200" style="fill:#0000ff;" />  
  <circle cx="125" cy="100" r="75" style="fill:#00ff00;" />  
</svg> 

HTML embed signature

<embed src="/workspace/files/shapes.svg" 
  width="250" height="200" type="image/svg+xml" />

The HTML embed tag shown above highlights that at the present time SVG files are usually stored as separate entities. It is possible to embed SVG directly into HTML, but some tricks are required - outside the scope of this introduction.

A more complex drawing

The following is a somewhat more complex SVG drawing, authored using an open source drawing tool known as Inkscape. I’m not showing the source for this drawing as it is quite long… for fancy effects Inkscape needs to include a lot in the file. You can even include textures, which get encoded in base64.

A complex SVG drawing

The same drawing zoomed 300%

Next is the same drawing… the only difference is that I zoomed the image in Inkscape by 300% to appear larger. The image still takes up only ~12Kb on disk… and only ~3.6Kb is sent from the server to the browser when compression is used. Notice that there is no degradation in the quality of the graphics, unlike the result when zooming a bit-mapped image file.

A complex SVG drawing at 300% zoom

Unfortunately I wasn’t able to apply a “dynamic zoom” for this image by simply changing what is known as the image viewport. Inkscape doesn’t allow for distances to be represented as a percentage of the window in which they are displayed. So instead I’ll revisit the first drawing in this article, modifying to SVG to demonstrate how the drawing can be made to fit an arbitrary window defined in the embed statement.

The simple drawing zoomed by (150%, 75%)

Simple SVG drawing at (150%, 75%) zoom

Corresponding SVG source

<svg xmlns="http://www.w3.org/2000/svg" version="1.1"
  width="100%" height="100%" viewBox="0 0 100 100" preserveAspectRatio="none">
  <rect x="0" y="0" width="100" height="80" style="fill:#0000ff;" />  
  <circle cx="50" cy="40" r="30" style="fill:#00ff00;" />  
</svg> 

HTML embed signature

<embed src="/workspace/files/shapes.svg" 
  width="375" height="188" type="image/svg+xml" />

By setting the coordinate system relative to the viewBox and preserveAspectRatio to “none” the SVG drawing takes its dimensions from the width and height tags in the EMBED statement. So one can scale drawings in arbitrary ways in the HTML tag.

Some advantages of SVG

Let’s consider some of the advantages SVG has over bit-mapped graphics… starting with the ones that have been most useful to me.

Textual description of graphics

There are times where working with bit-mapped graphics just doesn’t work well. Say you know in advance the exact position, shape, size and color of each “piece” of your diagram… it can be quite a bear to draw something like this by hand. Nor is an “automation interface” usually available to realize such a drawing should you wish to write a computer program to place each element in the diagram. SVG satisfies most of the requirements I had for effecting such drawings.

  • First and foremost, SVG is an open standard and is absolutely free. SVG drawings can be displayed by all major browsers today.
  • SVG is fully human-readable, with constructs like lines, rectangles, polygons and circles. Complex shapes are constructed moving a virtual cursor along a path.
  • SVG allows you to set up your own coordinate system, so you can use appropriate units (like millimeters) to describe the elements in your drawing.
  • SVG is hierarchical… as it is an XML dialect. This was useful to create collections of elements which I could display and hide using JavaScript.
  • SVG allows you to instrument a diagram file with comments - very handy when files become complex.

Diagrams are scalable

This might not sound like such a big deal, but it becomes important in a few situations. Say you need to represent a 2D canvas which is 150x150mm in size, consisting of a finite number of known shapes. When representing such a canvas using a bit-mapped format, you’ll need to establish your resolution (size represented by a single pixel) in advance. If you need 10um resolution, then the canvas in this example will need to be 15000x15000 in size… quite an impractical size, even when using compression. Contrast that with an SVG diagram, where you need not decide on the resolution beforehand… you merely zoom and let the rendering engine take care of the details.

While the obvious rendering engine is the common browser, there are other choices available. In my use-case, I needed to zoom regions of my canvas to a given resolution… and then save that zoomed image in bit-mapped form. For this task, I employed the Batik SVG Toolkit to render said regions of interest to bitmaps… in my situation, I called Batik from Java and rendered the regions of interest directly to memory.

Closing

I tried to convey some of the flavor and power of SVG in this article… but there are aspects of SVG which I’ve skipped (like animation!). I highly recommend following some of the links I’ve included in the above text and doing some reading. Inkscape is another great place to start, as it is free and easy to use.

Website Credits | Symphony | Fluid 960 Grid System