Treehouse

Generate Dojo GFX Drawings from SVG Files

By on  
SVG Dojo GFX

One of the most awesome parts of the Dojo / Dijit / DojoX family is the amazing GFX library.  GFX lives within the dojox.gfx namespace and provides the foundation of Dojo's charting, drawing, and sketch libraries.  GFX allows you to create vector graphics (SVG, VML, etc.) using a coherent, flexible API.  With GFX, you can create everything from static vector images to images that rotate, resize, animate, and basically anything you put your mind to creating.

I'll save going through the ins and outs of Dojo's GFX library for another time;  in this post, I'll focus on how you can take an existing SVG graphic and convert it into a Dojo GFX graphic in five minutes using Eric Brown's graphic converter!

The Setup

Obviously you'll want to download a fresh copy of the Dojo SDK.  Within the Dojo SDK you'll want to find the following directory:

dojox/gfx/resources/

Within the above directory you will find a svg2gfx.xsl file.  This file is the magic behind the conversion. You'll want to rename the file to svg2gfx.xslt for maximum capability with processor.

The Command Line Script

The command to run the script is as follows:

xsltproc svg2gfx.xslt YourSVGPhoto.svg > output.json

If you don't have the above package, you can easily find it with a quick Google search.

The Generated JSON

The result of running the script through the converter is a JSON file which will look something like this:

[
    {
        "name": "layer1",
        "children": [
            {
                "name": "g2623",
                "children": [
                    {
                        "name": "path6134",
                        "shape": {
                            "type": "path",
                            "path": "M168.724,99.136c-38.372,0-109.12,9.917-145.181,30.863 C-23.9,298.093,40.635,412.424,168.724,477.286c128.085-64.862,192.608-179.759,145.166-347.287 C277.829,109.054,207.094,99.136,168.724,99.136z"
                        },
                        "fill": "#9D864A",
                        "stroke": {
                            "color": "#9D864A",
                            "style": "Solid"
                        }
                    },
                    {
                        "name": "path5154",
                        "shape": {
                            "type": "path",
                            "path": "M168.724,109.948c-37.711,0-80.143,4.815-135.735,27.492 c-41.385,146.729,6.627,264.341,135.735,328.448C297.83,401.781,345.826,284.169,304.441,137.44 C248.849,114.763,206.437,109.948,168.724,109.948z"
                        },
                        "fill": "#012F73",
                        "stroke": {
                            "color": "#012F73",
                            "style": "Solid"
                        }
                    },
                    // More...

The JSON file could be relatively large (for a JSON file) but the flexibility we'll have with the end product is worth the size.

Rendering the JSON to a GFX Graphic

Hopefully you've found the process to be simple to this point.  Rendering the GFX image is equally as simple:

// Require dependencies
dojo.require('dojox.gfx');
dojo.require('dojox.gfx.utils');

// When loaded...
dojo.ready(function() {
	
	// Load image
	dojo.xhrGet({
		handleAs: 'json',
		url: 'arsenal.json',
		load: function(json) {
			
			// Create the surface
			var surface = dojox.gfx.createSurface("logoHolder", 500, 500);
			
			// Write JSON to group
			var group = surface.createGroup();
			dojox.gfx.utils.deserialize(group,json);
			
		}
	});
});

Start by requiring the dojox.gfx and dojo.gfx.util packages.  Using dojo.xhr you request the file via AJAX.  Once the image JSON has been successfully received, you create a GFX surface, a group within the surface, and use dojox.gfx.utils.deserialize to turn the JSON into a graphic.  Done!

So Why Do This?

There are a few advantages to using JSON and GFX to build and store your graphics:

  • GFX-managed graphics are easily animatable, scalable, and transformable
  • Load image data once but create the image many times at different sizes instead of needing more than one image
  • The GFX vector graphic will work within Internet Explorer, which it otherwise wouldn't if the image is SVG format

There you have it: painless graphic conversion and creation using Dojo's GFX library.  Check out my example or some of the examples that come with the Dojo SDK.

ydkjs-1.png

Recent Features

  • 5 More HTML5 APIs You Didnât Know Existed

    The HTML5 revolution has provided us some awesome JavaScript and HTML APIs.  Some are APIs we knew we've needed for years, others are cutting edge mobile and desktop helpers.  Regardless of API strength or purpose, anything to help us better do our job is a...

  • 9 Mind-Blowing Canvas Demos

    The <canvas> element has been a revelation for the visual experts among our ranks.  Canvas provides the means for incredible and efficient animations with the added bonus of no Flash; these developers can flash their awesome JavaScript skills instead.  Here are nine unbelievable canvas demos that...

Incredible Demos

  • Chris Coyier&#8217;s Favorite CodePen&nbsp;Demos

    David asked me if I'd be up for a guest post picking out some of my favorite Pens from CodePen. A daunting task! There are so many! I managed to pick a few though that have blown me away over the past few months. If you...

  • Font Replacement Using&nbsp;Cufón

    We all know about the big font replacement methods. sIFR's big. Image font replacement has gained some steam. Not too many people know about a great project named Cufón though. Cufón uses a unique blend of a proprietary font generator tool...

Discussion

  1. Hi David,

    This is a very interesting article. I’m a big fan of your work :)
    I just have one question concerning the GFX library and the svg format.
    Do you know how are handled the a xlink:href elements if defined in a svg graphic ?
    I basically have a svg graphic containing elements where id and xlink are defined and look for a svg replacement solution ..

    Thx,
    Kevin

  2. ric

    image doesn´t render well on ie, and animation doesnt work maybe there´s something like a fix for this, now with the latest version of dojo?

  3. dragonfly

    I have dojo toolkit 1.7.0 installed .. and tested.

    I’ve followed the tutorial .. closely .. but there is no rendering of SVG > GFX in my browser (Firefox 8.0). The SVG can be viewed on its own. A json file was created using command line xstlproc …

    The test svg came from here .. http://croczilla.com/bits_and_pieces/svg/samples

    circles1.svg was transformed to circles.json ..


    [{children:[{shape:{type:"circle",cx:6.5cm,cy:2cm,r:100,},fill:"red",stroke:

    {color:"black",width:"0.1cm",style:"Solid",},transform:{dx:0,dy:50,}},{shape:

    {type:"circle",cx:6.5cm,cy:2cm,r:100,},fill:"blue",stroke:

    {color:"black",width:"0.1cm",style:"Solid",},transform:{dx:70,dy:150,}},{shape:

    {type:"circle",cx:6.5cm,cy:2cm,r:100,},fill:"green",stroke:

    {color:"black",width:"0.1cm",style:"Solid",},transform:{dx:-70,dy:150,}}]}]

    And the html wrapper was created ..


    // ......

    handleAs: 'json',
    url: 'circles.json',
    load: function(json) {

    // Create the surface
    var surface = dojox.gfx.createSurface("circlescontent", 600, 600);

    etc.

    // ......

    but no image is rendered in div id=”circlescontent”.

    How do we troubleshoot the rendering process?

    I’ve posted a similar question on the dojo community forum ..

    http://dojotoolkit.org/community/

  4. Hi David,

    Dojo GFX looks like an awesome tool – we’re busy with a mobile/tablet web-app and need some SVG graphics, but Android doesn’t support SVG. Do you know if the Dojo GFX vector graphics is Android compliant? It’s would be a map with click events, etc – so some kind of interaction will be required.

    Thanks bro,

    Cam

    • I’m not sure what Android-compliant means, but gfx works on damn near everything. My former boss once created a pong game with GFX, created for the wii, where you used wiimotes for paddles. Mental! If you have an Android device handy, you can hit one of my demos to see if it measures up:

      http://dojotoolkit.org/documentation/tutorials/1.8/gfx/

  5. Just trying to follow the example above. Downloaded the latest Dojo Toolkit 1.8. Managed to create JSON file with xlstproc.exe (from http://www.zlatkovic.com/libxml.en.html) and the conversion seems fine. Tried the sample code and cannot see SVG code rendered.

    Maybe it is because I cannot find the required files in the Dojo Toolkit 1.8
    dojo.require(‘dojox.gfx’);
    dojo.require(‘dojox.gfx.utils’);

    1. Where would these files reside?
    2. Would you have complete code to run the example to learn about it (not just code snippets).

    Thank you. Br, Jukka

  6. qaspok

    Cool idea. Unfortunately the conversion is failing for me. I tried converting a simple one color logo and ended up with some missing line segments.

  7. qaspok

    OK, after doing some troubleshooting I figured out the problem that people seem to be having. If you open up svg2gfx.xsl and read the comments you will find that the converter only covers a small subset of what SVG can do. If your SVG file contains features that are not available in the converter you will get a blank screen when you try to load the json file.

    For me the problem was transforms. When sizing or moving an image using the Inkscape graphic editor, rather than changing the co-ordinates of each point, Inkscape adds a transform to the SVG file. The solution for me was to select Path->Simplify from the in Inkscape.

    Additionally, the image was coming out garbled. Saving the file as a ‘Optimized SVG’ in Inkscape produced a file which is arrange similarly to the svg2gfx output.

    No more problems!

  8. Sergey

    Hi, David!
    I trying to get a JSON file from saving in INKSCAPE SVG file using “xsltproc svg2gfx.xslt …” but as result I have the not valid JSON without double quotes in the all property names.
    How can I solve this problem?
    Many thanks

Wrap your code in <pre class="{language}"></pre> tags, link to a GitHub gist, JSFiddle fiddle, or CodePen pen to embed!