XML.com: XML From the Inside Out
oreilly.comSafari Bookshelf.Conferences.

advertisement

An Introduction to Scalable Vector Graphics

March 21, 2001

If you're a web designer who's worked with graphics, you may have heard of Scalable Vector Graphics (SVG). You may even have downloaded a plug-in to view SVG files in your browser. The first and most important thing to know about SVG is that it isn't a proprietary format. On the contrary, it's an XML language that describes two-dimensional graphics. SVG is an open standard, proposed by the W3C:

SVG is a language for describing two-dimensional graphics in XML. SVG allows for three types of graphic objects: vector graphic shapes (e.g., paths consisting of straight lines and curves), images and text. Graphical objects can be grouped, styled, transformed and composited into previously rendered objects. The feature set includes nested transformations, clipping paths, alpha masks, filter effects and template objects.

SVG drawings can be interactive and dynamic. Animations can be defined and triggered either declaratively (i.e., by embedding SVG animation elements in SVG content) or via scripting.

This article gives you all the basic information you need to start putting SVG to use. You'll learn enough to be able to make a handbill for a digital camera that's on sale at the fictitious MegaMart. (Any resemblance of this camera to a real product is slightly coincidental.)

finished handbill

Initialization

We want the handbill to be the size of a half sheet of U.S. letter paper. We specify that in the <svg> tag below. You should always include <title> and <desc> elements. SVG display programs use the title to display a tooltip, and the description is useful for search engines. Additionally your document will be more easily accessible to visually impaired users.

<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20001102//EN"
   "http://www.w3.org/TR/2000/CR-SVG-20001102/DTD/svg-20001102.dtd">

<svg width="21cm" height="13.5cm">
<title>MegaMall Handbill</title>
<desc>
    Handbill for the fictitious MegaMall
</desc>
    <!-- graphic specifications go here -->
</svg>

The DOCTYPE declaration above is not final yet because SVG is not a recommendation, although it is expected to gain that status soon.

When specifying width and height, you are actually establishing a viewport in which your drawing will be displayed. You may use em, ex, px, pt, pc, cm, mm, or in to specify dimensions. If you don't use a measurement unit, then the numbers are assumed to be pixels (px).

UnitMeaning
em a unit equal to the current font size
ex the x-height, usually the height of a lower case letter x
px pixels (the default)
pt points (one point = 1/72 inch)
pc picas (one pica = 1/6 inch)
cmcentimeters
mmmillimeters
ininches

All numbers used to measure coordinates are assumed to be the same unit-type used to establish width and height. In our handbill, we'll set the width="21cm" and height="13.5cm". In order to avoid having to use decimals for all of the coordinates, we will establish a viewBox. A viewBox sets up a user coordinate system which is mapped into the viewport bounds, stretching or shrinking a graphic if the viewBox and viewport aren't proportional. This stretching and shrinking happens only if the preserveAspectRatio is set to none (which is not the default). In the following specification, we set up a system with ten "units" per centimeter.

<svg id="body" width="21cm" height="13.5cm"
    viewBox="0 0 210 135">

Adding Graphic Elements

Let's start off by adding the red-bordered rectangle with the light blue interior.

<svg id="body" width="21cm" height="13.5cm"
    viewBox="0 0 210 135">
<title>Example 1</title>
<desc>
    Rectangle with red border and light blue interior.
</desc>
 <rect x="10" y="20" width="150" height="70"
        fill="#eeeeff" stroke="red" stroke-width="1" />
</svg>

You specify a rectangle by giving the x and y coordinates of its upper left corner and its width and height. When specifying coordinates, the positive x direction is to the right, and the positive y direction is downwards.

In this case, we've also set the fill color, stroke (line) color, and stroke-width as separate attributes. It's also possible to set all these properties, in a way similar to CSS, by way of a style attribute, an internal style sheet, or an external style sheet. You can look at the SVG file for the style attribute or for the internal style sheet.

Here's the result, shown at half size:

red-bordered rectangle with light blue interior

If you'd like to try this yourself, download the Apache Software Foundation's Batik tool and install it according to its instructions. You will need a Java VM version 1.2 or greater. You can invoke the viewer tool with a simple UNIX command line like

# use path appropriate to where you've installed batik
java -jar /usr/local/xml-batik/batik/batik-svgviewer.jar

Transformations

Let's add the gray drop-shadow rectangle. We want it three units to the right and below the red rectangle. Rather than do the addition of the x and y coordinates ourselves, we can specify that SVG should perform a transform on the graphic; it should translate the rectangle by three units in both dimensions. Here's the SVG, followed by the resulting image.

<svg id="body" width="21cm" height="13.5cm"
    viewBox="0 0 210 135">
<title>Example 2</title>
<desc>
    Rectangle with red border and light blue interior,
    with (intended) gray shadow rectangle.
</desc>
    <rect x="10" y="20" width="150" height="70"
        fill="#eeeeff" stroke="red" stroke-width="1" />

    <rect x="10" y="20" width="150" height="70"
        transform="translate(3, 3)"
        fill="#999999" stroke="#999999" stroke-width="1" />
</svg>

gray rectangle atop red rectangle

Not exactly what we had in mind. This demonstrates one of the rules of SVG: if object B is specified after object A in the source file, it appears above object A. We simply reverse the order in which the rectangles appear to get the desired result.

<svg id="body" width="21cm" height="13.5cm"
    viewBox="0 0 210 135">
<title>Example 3</title>
<desc>
    Rectangle with red border and light blue interior,
    with gray shadow rectangle.
</desc>
    <rect x="10" y="20" width="150" height="70"
        transform="translate(3, 3)"
        fill="#999999" stroke="#999999" stroke-width="1" />

    <rect x="10" y="20" width="150" height="70"
        fill="#eeeeff" stroke="red" stroke-width="1" />
</svg>

red rectangle w. gray shadow

Reusing Graphics

green loop Next we'll put in the green loops above and below the rectangle. If you look closely, you'll see that it's just one loop repeated over and over again. By putting the description of the single loop inside the <defs> element, you specify that you are defining a graphic for later use, but do not want it displayed immediately. So you add this immediately after the </desc>. (Line numbers are shown for reference only.)

 1 <defs>
 2  <polyline id="loop"
 3      points=
 4       1.00,  0.00     0.93,  0.16
 5       0.72,  0.26     0.43,  0.25
 6       0.13,  0.11    -0.11, -0.13
 7      -0.25, -0.43    -0.26, -0.72
 8      -0.16, -0.93     0.00, -1.00
 9       0.16, -0.93     0.26, -0.72
10       0.25, -0.43     0.11, -0.13
11      -0.13,  0.11    -0.43,  0.25
12      -0.72,  0.26    -0.93,  0.16
13      -1.00,  0.00"
14      transform="scale(5, 5)"
15      stroke="green" stroke-width="0.1" fill="none" />
16 </defs>
Line 1
Start “definitions” area.
Line 2
A polyline defines a set of connected straight line segments. The id attribute gives the object a unique name by which you can refer to it.
Lines 3-13
The points attribute lists the (xy) coordinate pairs for each point in the line segment. These points happen to be a graph of the polar equation r = 2cos(a) where a ranges from 0° to 180°, generated by this Java program. That's why the coordinates all range from -1 to 1 in the x and y directions. You may use commas and/or whitespace to separate coordinate values.
Line 14
To make the loop large enough to see, we use the scale transformation to multiply coordinates by 5 in both the x and y directions. Important: all coordinates for this object are now scaled by a factor of five.
Line 15
Specifies the line color to be green. Note that we have to set the stroke width to 0.1, because it, too, will be multiplied by five.

Then, after drawing the rectangles, you <use> the object that you defined, translating it to the proper place on the canvas. The <use> element's xlink:href will be the URI of the resource to use. It produces the result shown below. See source code

<rect x="10" y="20" width="150" height="70"
    fill="#eeeeff" stroke="red" stroke-width="1" />

<use xlink:href="#loop" transform="translate(20,100)"/>

red rectangle w. gray shadow and one green loop

Pages: 1, 2

Next Pagearrow







close