Wrox Press
ASPToday
       944 Articles
  in the Solutions Library
  Log off
 
 
 
VSLive!  
 
ASPToday Subscriber's Article Costas Hadjisotiriou
A 3D Visualizer in Vector Markup Language
by Costas Hadjisotiriou
Categories: Other Technologies
Article Rating: 3
Published on September 18, 2002
 
Content Related Links Discussion Comments Index Entries Downloads
 
Abstract
The Vector Markup Language (VML) is a very efficient method for presenting shapes that would take a lot of network resources to deliver as raster images. Despite the fact that it has been supported since Internet Explorer 5.5, VML has not been adopted as one would imagine – even taking into account cross-browser support issues. In this article, Costas Hadjisotiriou will look at the capabilities of VML, examine some extra features not documented in the W3C specification, and find out what it can do for the user experience, by creating a 3D visualizer out of simple HTML tags.
 
 
Article

Anatomy of VML

The idea behind VML is that many images that exist today as bitmaps on web pages would be better represented via vector drawing. For example, any image that contains text - if the text content has to be changed the whole image has to be recreated from scratch. With VML, the designer only has to retype the text. VML is also scalable with no additional byte cost. A square shape of 10px by 10px claims the same transmission kB in the web page as any other size implementation of it, 1000px by 1000px, say. The third and most critical advantage over raster images is that the VML-shape contents are accessible via client script. The shapes can be added, erased and modified programmatically, enabling a live and interactive user interface.

VML is not appropriate everywhere, especially not where "arty" images are required - as a rule of thumb, where a GIF format would be preferable to a JPEG then VML would probably be even better. An example would be a graph, a cartoon, or a geometric shape like the one shown below:

The code used for producing the shape is this (_vml_first.html):

<HTML xmlns:v="urn:schemas-microsoft-com:vml">
<HEAD>
<STYLE>
v\:* { behavior: url(#default#VML);} 
</STYLE>
<TITLE>VML Sample</TITLE>
</HEAD>
<BODY>

<table>
<tr><td>
<v:shape id="test" fillcolor="yellow"
style="position:relative;top:1;left:1;width:700px;height:700px;rotation:0;" 
coordsize="1000,1000"
   path = "m 200,200 l 400,300, 400,500,  200,600, 1,500, 1,300 x 
           m 200,250 l 350,320, 350,480,  200,550, 50,480, 50,320 x e">
   </v:shape>
</td></tr>
</table>
    
</BODY>
</HTML>

We will see an explanation of how the shape is drawn with the next shape - firstly, there are three important areas to look at:

  • The namespace declaration
  • The definition of the behavior for the v: tag prefix
  • The creation of the shape itself

The namespace and behavior declarations are the minimum required for a shape to be created. Although Microsoft's documentation specifies an additional namespace of Microsoft Office Extensions (tag prefix o:) it is not required for web applications - it is used by applications like PowerPoint and Visio.

One of the main objectives of the VML Group of the W3C (composed of Microsoft, Visio, Autodesk, Hewlett Packard and Macromedia) was that the processing model of VML should be the same as HTML. This is so that the wheel does not have to be reinvented for functionality that exists in the HTML or CSS infrastructure. Like HTML, VML describes objects, which will often be further edited. In the case of HTML, these objects are paragraphs, forms or tables. In the case of VML, the objects are shapes.

Backward and forward compatibility is also easily achieved by using the namespace declaration so that older browsers can ignore the unknown tags. Let's look at the most generic tag, <v:shape> a bit more closely by analyzing its most important attributes:

Copyright © 1998 W3C All Rights Reserved. http://www.w3.org/Consortium/Legal/?WROXEMPTOKEN=55322ZWhkXjJQlY4zPJFFnpWa1 Status:submission

Namespace Attribute Description
VML id A unique ID that identifies the shape so that scripts can reference it.
VML type A reference to a shapetype id that describes the standard path, fill and stroke properties of a shape. If any of these properties are re-defined in the shape they will override the shapetype properties.
VML adj A list of numbers separated by commas, that are the parameters passed onto the guide formulas that define the path of the shape. There can be up to 8 adjust parameters.
VML path A string containing the commands that define the path. We will examine the path definition in detail later.
CSS visibility If hidden the shape is not rendered and does not generate mouse events.
CSS top, margin-top, center-y, etc The position of the top of the containing block of the shape in CSS units. If the element belongs to a group, then the units are the coordmap units of the parent element. We will look at using parent-child coordinates later.
CSS left, margin-left, center-x, etc The position of the left of the containing block of the shape, as above
CSS width The width of the container rectangle of the shape. In CSS units or, for elements in a group, in the coordmap units of the parent element.
CSS height The height of the containing block of the shape in CSS units or, for elements in a group, in the coordmap units of parent element.
CSS z-index The z-index of the shape. Positive numbers are in front of the screen. Negative numbers are behind the screen.
CSS rotation The angle to rotate the reference rectangle. Positive angles are clockwise.
CSS flip Takes values "x" or "y" or both. Indicates that the shape image inside the reference rectangle should be flipped as appropriate along the listed axes in the order specified. i.e. flip: x means flip about the y-axis so that x becomes -x.
CSS position May be any CSS value when this is a top-level element. When it is contained inside a group, it must always be absolute.
VML opacity The opacity of the entire shape. A fraction between 0 (completely transparent) and 1 (completely opaque.)
VML chromakey A color value that will be transparent and show anything behind the shape.
VML fill If true, the path defining the shape will be filled. By default, it will be filled using a solid color unless there is a <fill> sub-element that specifies more complex fill properties. If false, the fill is transparent.
VML fillcolor The primary color of the brush to use to fill the path of this shape.
VML v A string containing the commands that define the path - see also the W3C documentation on the use of formulas to define the path.
VML print If true, this shape can be printed.
VML coordsize The number of units that the width and height of this shape is divided in. This defines the x and y of the coordinate space inside the containing block of this shape. If it is not specified, it is the same as the width and height of the rectangle.
VML coordorigin The coordinates at the top-left corner of the containing block.
VML wrapcoords In the form "x1,y1,x2,y2,x3,y3..." (same as coords in an AREA). Describes in drawing units around a shape. Used for the wrapping of text around an object.

Note that because VML supports CSS2 style properties there is more than one way of defining certain attributes. For example, rotation can be specified within the style attribute (as we have done in our example above) or via a separate rotation attribute - both have the same effect of course.

The most critical attribute is path:

path = "m 200,200 l 400,300, 400,500,  200,600, 1,500, 1,300 x 
        m 200,250 l 350,320, 350,480,  200,550, 50,480, 50,320 x e"> 

The numbers inside the path string refer to a coordinate system of our choosing. They can use various units of measurements, e.g. pixels (px), millimetres (mm), points (pt), but we can create a local unitless coordinate system as follows:

coordsize="1000,1000"

This allows us to design our shape and resize it freely by changing the width and height elements of the style attribute. Otherwise, if we wanted to resize the shape we would have to change every single coordinate in the path! Make sure that the ratio of width to coordsize(x) is the same as height to coordsize(y), otherwise the shape will appear distorted.

To understand how the path element draws vectors we need to look at the commands used within it - a full list can be found in the W3C specification, but here are the ones we will be using in this article:

Copyright © 1998 W3C All Rights Reserved. http://www.w3.org/Consortium/Legal/?WROXEMPTOKEN=55322ZWhkXjJQlY4zPJFFnpWa1 Status:submission

Command Parameters Description
m 2 Start a new sub-path at the given (x,y) coordinate
l 2* Draw a line from the current point to the given (x,y) coordinate which becomes the new current point. A number of coordinate pairs may be specified to form a polyline.
c 6* Draw a cubic bézier curve from the current point to the coordinate given by the final two parameters, the control points given by the first four parameters.
x 0 Close the current sub-path by drawing a straight line from the current point to the original moveto point.
e 0 End the current set of sub-paths. A given set of sub-paths (as delimited by end) is filled using eofill. Subsequent sets of sub-paths are filled independently and superimposed on existing ones.
wa 8* Draw arc in a clockwise direction using the first 4 values (left, top, right, bottom) to define the bounding box of an ellipse, and the last four (start(x,y) end(x,y)) as the definitions of two radial vectors. A line is drawn from the current point to the start of the arc.
wr 8* As above, but with an implied move (command m) to the first point (i.e. no line is drawn to the starting point).
qx 2* Draw a quarter ellipse from the current point to the given end point. The elliptical segment is initially tangential to a line parallel to the x-axis. (i.e. the segment starts out horizontal)
qy 2* Same as above except that the elliptical segment is initially tangential to a line parallel to the y-axis. (i.e. the segment starts out vertical)

* means any number of consecutive parameter groups.

You can make really complicated shapes with these commands:

This was created with less than 1Kb of code (_vml_ionic.html), and of course with lots of patience:

coordsize="500,250" 
path = "m 100,125 qy 75, 150 qx 50, 110 qy 110, 75 qx 150, 150 qy 75, 200 
  l 0, 200 l 0, 250 l 500, 250 l 500, 200 l 75, 200
  qx 0, 100 qy 105, 25
  l 0, 25 l 0, 0 l 500, 0 l 500, 25 l 105, 25  
  c 170, 40, 200, 70, 250, 90 c 300, 70, 330, 40, 395, 25
  qx 500, 100 qy 425, 200 qx 350, 150 qy 390, 75 qx 450, 110 qy 425, 150 qx 400, 
  125  l 399, 125 qy 425, 151 qx 451, 110 qy 390, 74 qx 339, 135 qy 250, 200 
  qx 161, 135 qy 110, 74 qx 49, 110 qy 75, 151  
  qx 101, 125  
  x e">

whereas the image you see above is more than 5Kb.

The path string above can be translated in English as follows:

  • m 100, 125 = move to coordinate point x=100, y=125 without writing anything
  • qy 75, 150 = draw an elliptic quadrant that starts from the current point (100,125), moves initially in the y direction (downwards or upwards, not horizontally), and finish at the point x=75, y=150
  • qx 50, 110 = draw an elliptic quadrant again, initially moving horizontally, ending at the specified point

A few more instructions further down we see:

  • l 0, 200 = draw a straight line from current point to x=0, y=200
  • c 170, 40, 200, 70, 250, 90 = draw a cubic bézier curve to point x=250, y=90, as modified by points x=170, y=40 and x=200, y=70.

The rest of the instructions are easy to follow.

As mentioned earlier, the W3C specification provides a comprehensive example and a lot of information on using VML. However, it contains no information on one very important Internet Explorer implementation detail: the <v:extrusion> subelement. We will be looking at how we can use that to produce a useful, network-efficient, portable 3D visualizing tool.

Three Dimensional VML

Let's go back to our modest hexagon shape. We can create a simple JavaScript interface (_vml_simple.html) for changing shape and extrusion attributes, hopefully making it easier to visualize the effect of each change. Behind each table cell in the screenshot you see below, there is a script function that sets a shape attribute - for example, hovering over the 3D type toggle cell we can change the value of the type attribute from perspective to parallel and vice versa. The lower / higher cells introduce a timer that calls themselves repeatedly, as long as the mouse is kept hovering over them. We won't analyze the JavaScript functions here, they were simply written to automate the changing of the attributes.

As you can see, with 3D we have some new attributes - a table follows later which describes them in detail. Before that, here is an image of how our hexagon looks in 3D (after modifying some attribute values via the lower / higher cells) and then an explanation of how the <v:extrusion> sub element was used to achieve that:

<v:shape ..... >
...
<v:extrusion id="testchild" on="True" BackDepth="50" lockrotationcenter="true" 
type="parallel" color="yellow" skewangle="0" Orientation="0.1, 0.2, 0.5"  
Orientationangle="-90" skewamt="0%"  
Viewpoint="-125000emu, 1250000emu"  Viewpointorigin="0.3, 0.1" />
...
</v:shape>

Not bad functionality for 4 lines of code. As you can see the extrusion element is contained within the shape tags. The id attribute enables it to be referred in script - the rest of the attributes are slightly more complex:

Table content copyright © Microsoft Corp.

Attribute (grouped by function) Description
Editing
On Determines whether an extrusion will be displayed.
Ext Defines the default extrusion behavior for graphical editors.
Design  
Type Defines the way that the shape is extruded, perspective or parallel.
BackDepth Defines the amount of backward extrusion.
ForeDepth Defines the amount of forward extrusion.
Plane Specifies the plane that is at right angles to the extrusion, xy (default), yz, xz.
SkewAmt Defines the amount of skew of an extrusion.
SkewAngle Defines the angle of skew of an extrusion.
Edge Defines the apparent bevel of the extrusion edges.
Facet Defines the number of facets used to describe curved surfaces of an extrusion.
Viewing
AutoRotationCenter Determines whether the center of rotation will be the geometric center of the extrusion.
LockRotationCenter Determines whether the rotation of the extruded object is specified by the RotationAngle attribute. Default False
RotationCenter Specifies the center of rotation for a shape.
RotationAngle Specifies the rotation of the object about the x- and y-axes.
Orientation Specifies the vector around which a shape will be rotated (i.e. a more flexible RotationCenter).
OrientationAngle Defines the angle that an extrusion rotates around the orientation.
Viewpoint Defines the viewpoint of the observer.
ViewpointOrigin Defines the origin of the viewpoint within the bounding box of the shape.
Appearance
Color Defines the color of the extrusion faces.
ColorMode Determines the mode of extrusion color, auto, custom (i.e. value of the Color attribute).
Brightness Specifies the amount of brightness of a scene.
Diffusity Defines the amount of diffusion of reflected light from an extruded shape.
LightFace Determines whether the front face of the extrusion will respond to changes in the lighting.
LightHarsh Determines whether the primary light source will be harsh.
LightHarsh2 Determines whether the secondary light source will be harsh.
LightLevel Defines the intensity of the primary light source for the scene.
LightLevel2 Defines the intensity of the secondary light source for the scene.
LightPosition Specifies the position of the primary light in a scene.
LightPosition2 Specifies the position of the secondary light in a scene.
Metal Determines whether the surface of the extruded shape will resemble metal.
Render Defines the rendering mode of the extrusion, solid, wireframe, boundingcube.
Shininess Defines the concentration of reflected light of an extrusion surface.
Specularity Defines the specularity of an extruded shape.

There are definitely a lot of tags and attributes. Microsoft provides a simple VML tag generator that can do simple typing for you, but it is not a graphical editor. The 3D section lists all the available attributes, which you can enter by clicking:

In the bottom left corner you can also see the Shape Types drop down list - it creates special cases of the <v:shape> element, using different tags, for example oval, rect, arc, roundrect etc. I personally use the editor mainly to look up tag names and get some default values. You can get it from http://msdn.microsoft.com/downloads/samples/internet/default.asp?url=/downloads/samples/internet/vml/vmlgenerator/default.asp&WROXEMPTOKEN=55322ZWhkXjJQlY4zPJFFnpWa1.

So we have a form of simple 3D visualizer - however, we can combine a variety of the above attributes to create an extended-functionality 3D environment.

Multiple Shapes

In the file _vml_ballroom.html of the download material you can see the code with which the two shapes below were drawn. With a bit of imagination you can see male and female ballroom dancers:

Note that there is not yet an easy way that I know of to draw the curves - it is mostly trial and error. The two path shapes are enclosed together in a <v:group> super element which enables us to treat them as one item. Unfortunately, this only applies to rotation around the z-axis, since the <v:group> element does not have a RotationAngle attribute. Instead we can rotate (or change any other attribute) our two shapes separately, but in-sync. So, with the values shown in the screenshot below we can have a flying dancing couple:

If you want to avoid overlapping the shape with the text you can use standard CSS2 positioning techniques, for example in the style attribute of the <v:group> element:

style="position:relative;top:1;left:200;"

The way to achieve the synchronized rotation around the y-axis is by arranging the rotation center of the first shape as:

rotationcenter="0.5,0.5"

and of the second shape as:

rotationcenter="-0.5,0.5"

which means that the axis around which the two shapes rotate is located at the same point (rightmost for the first shape, which is also the leftmost for the second shape).

Another possibility is to display one of the extruded shapes on a different plane, thereby creating any form of real-life object. Taken further, this could mean the creation of an HTML-only version of "virtual reality" with quite realistic results (see the below image from _vml_athens.html). I put virtual reality in quotes because when the shapes are rotated the z-index (the order of which shape overlaps the others) is not automatically adjusted. It can obviously be handled in code, but that would be specific for each and every shape - hardly the virtual reality technology we need!

In addition, the technology does not appear to be completely ready. The picture below shows the same object as above, slightly rotated. As you can see, the rendering of the curved extrusion is imperfect (to put it mildly). It looks as though the inner layer of curved extrusion somehow prevents the outermost curve from rendering.

A rotationangle value higher than 0 seems to correct the problem, but obviously this means that curved extruded surfaces are not completely ready for 3D display. The download material contains the relevant code and you can perhaps find a suitable solution.

Conclusion

VML is definitely a powerful and flexible drawing language. The imagination of the developer is the only limit for producing highly interactive interfaces, product displays, 3D maps and graphs, low-download-size pictures and so on.

Hopefully you will have found this article to have been a useful introduction to this exciting technology.

 

Please rate this article using the form below. By telling us what you like and dislike about it we can tailor our content to meet your needs.

Article Information
Author Costas Hadjisotiriou
Chief Technical Editor John R. Chapman
Project Manager Helen Cuthill
Reviewers John Boyd Nolan & Sauranh Nandu

If you have any questions or comments about this article, please contact the technical editor.

 
 
Rate this Article
How useful was this article?
Not useful Very useful
Brief Reader Comments: Read Comments
Your name (optional):
 
 
Content Related Links Discussion Comments Index Entries Downloads
 
Back to top