SVG runtime importer for getting vector shapes into Unity

Posted by admin on August 8, 2011 in Unity3d |

I needed to load some basic simple polygon shapes into Unity at runtime and get it there in form of the meshes.  There are already some resources on Unity Community Wiki on import of svg files, but they regard to rendering those files to textures. I was wondering whether I could rex make the scripts by making them just to generate the sequences of points instead of rendering the whole images, but they seemed too complicated and to make things worse I got discouraged, because they were written in C#. On the other hand svg polygon specification seemed very simple, so my final choice was to write it from sctratch. The next step was to triangulate the polygons i.e. to fill them with triangles. I didn’t intend to go beyond the simple basic shapes so I have chosen the ear clipping method of triangulation which supports supports concave polygons, but not polygons with holes, or multiple polygons combined. This method is followed by the Triangulator script from Unify Community Wiki.

I have learned soon that a simple polygon shapes of identical appearance can take forms of various svg elements like “polygon”, “polyline”, “rect” (as rectangle) and “path”.   From the above the “path” is most complicated, because can contain a number of internal commands.

All the elements can have attributes like name (“id”), color, opacity, transform, style, etc. I have selected to support in my simple importer only name, color, opacity and transform on rectangle element only. The color and opacity of the element transforms into properties of material in Unity.

In order to manipulate the colors which are specified in hexadecimal values as svg attributes, I have used two more scripts from the Wiki, i.e. HexConverter and HSBColor.

You can download the sources from here:

2469 Downloads

I have tested it with files saved from Inkscape, Coreldraw and Illustrator. Please let me know if you get any errors or have some suggestions for improvement. The download contains the complete Unity3d project folder.

The tree image used in this example come from here: http://www.allfreevectors.com

Because my simple importer doesn’t support multiple/combined paths, the closed shape letters in the lettering example had to be opened by cutting them.

Recently I have added some interaction to this example, mouse clicking at the front side ot the graphic toggles the fill/outline display.

14 Comments

  • rraallvv says:

    I don’t know the language your script is written for. Can it be ported to C++, in order to parse a SVG and render it using OpenGL ES 1.1, the one that is available for iphone?

    • admin says:

      This is for the special javascript dialect used in Unity3d. Ported t C++? Why not? Be aware svg has many strandards depending on the program you draw and save and I have been testing that on Illustrator and Coreldraw. Recently I did some tests on inkscape – the native app for svg format and I found some problems with it. Generally svg’s often use xml standards in organizing data I made too little use of that in interpreting the file.

      • Pratik Parikh says:

        Is there any work around for inkscape? as it is a free software. I tried making the svg in illustrator its working fine for the normal color fill , but for some complicated vector by making curve shapes & for gradient fill its giving problem. it is just showing the black borders do you have any idea about this or is there something i am doing wrong ?

  • Olivier says:

    Thank you very much for this,
    I have now achieved something similar but I have used Xpath to extract the info needed from the svg file, and you work is not be used for commercial use anyway 😉
    Thank you for the inspiration though…

    • admin says:

      Sounds interesting. I was wondering if I could use xml, but It didn’t seem to me much easier. Does use of Xpath simplify that?
      BTW, since the publication of that I have also added a mesh extrusion to that because I needed that for some demos.

      • Olivier says:

        I have also added mesh extrusion!! for this demo on my latest facebook post: https://www.facebook.com/olivier.m.etienne
        mesh optimisation script to remove potential unused vertices, I bet you did that too!!
        Back to your question….
        Your code is very clear and very well written,
        but Xpath is design for XML so yes it does simplify it and also makes the code a lot easier to understand. The extraction of the attribut “d” (I am using inkscape) needed is done like so:
        root.Select(“//svg:path”,nsMgr);// return all paths in the xml file
        iterator.MoveNext();//work on the first path in the svg
        iterator.Current.GetAttribute(“d”, “”); //Give me the d attribute ie:vertices
        verticeSvg.Split(” “[0]);// make an array out of that please
        There you have it!!!
        I must warn you though, Once you go Xpath you can’t go back!!!

        • admin says:

          Sounds fantastic. Possibly I will get back to it using the xpath when I have time. But the main problem I encountered was the same interpretation of the same svg graphics saved from different common softs like inkscape, coreldraw, illustrator, freehand ets. Perhaps using xpath will be also be a remedy for that. Can you share your script?

      • Olivier says:

        Sorry for the delay in replying, but your CatchPa has given me such a hard time!!!
        My code is so untidy it would be disrespectful to post that mess on such a tidy page!!!
        But I’ll give you what you need to get you started:

        If you use Insckape
        {
        First create a path in inkscape
        From the path menu, select Path -> Object to Path
        From the file menu select Vacuum def to remove the unwanted path def
        }

        //HERE THE JAVASCRIPT
        import System.Xml;
        import System.Xml.XPath;
        //HERE I AM IMPORTING THE LIBRARY NEEDED

        var xmldoc:XPathDocument = new XPathDocument(Application.dataPath + “/SVG/poly.svg”);
        //THE SVG FILE NAME poly.svg IS LOCATED IN A SVG FOLDER in the Asset folder

        var root:XPathNavigator = xmldoc.CreateNavigator();
        //CREATE A NAVIGATOR

        var nsMgr:XmlNamespaceManager = new XmlNamespaceManager(root.NameTable);
        //CREATE A NAME SPACE MANAGER

        nsMgr.AddNamespace(“svg”, “http://www.w3.org/2000/svg”);
        //ADD ALL THE NAMESCAPE NEEDED IN THIS CASE I ONLY NEED SVG BECAUSE IT CONTAIN ALL THE PATH AND G ELEMENT (MIGHT BE DIFFERENT IN ILLUSTRATOR, BUT I HAVE TRIED BECAUSE I ONLY USE FREE AND OPEN STUFF!!)

        var iterator : XPathNodeIterator = root.Select(“//svg:path”,nsMgr);
        //CREATE AN ITERATOR

        iterator.MoveNext();
        ///SELECT THE FIRST PATH ELEMENT

        var verticeSvg:String = iterator.Current.GetAttribute(“d”, “”);
        //GET THE D ATTRIBUT WHICH RETURN:
        //d=”M 20.234,939.73 0.60387,943.39 0.60387,1022.8 11.854,1025.8 //22.724,987.81 20.534,940.04 z”

        var strVertices:String[] = verticeSvg.Split(” “[0]);
        //PUT THAT IN AN ARRAY TO MANIPULATE EASILY
        //FROM THERE YOU CAN PRETTY GUESS THE REST AS I EXTRACT THE INFO FOR //VERTICE2D

        //SOME MORE XPATH PRACTICE NOW:

        //THIS EXTRACT THE ID OF THE PATH
        var namePath:String = iterator.Current.GetAttribute(“id”, “”);

        //THIS EXTRACT THE WIDTH AND HEIGHT AT THE BEGINNING OF THE SVG FILE
        iterator = root.Select(“//svg:svg”,nsMgr);
        iterator.MoveNext();
        var width:String = iterator.Current.GetAttribute(“width”, “”);
        var height:String = iterator.Current.GetAttribute(“height”, “”);

        HOPE THAT’S ENOUGHT TO GET YOU STARTED, LET ME KNOW IF I CAN BE OF ANY HELP, PLEASE EMAIL AS I HAVE MADE YOUR BLOG UNTIDY ENOUGHT!!!

        I DON’T COPYRIGHT THAT, PLEASE USE FOR ANY PURPOSES INCLUDING COMMERCIAL.

        HAPPY XPATH!

  • John Collins says:

    Hi,
    really nice written article.
    I was looking for some Unity ready to go solution
    and recently I came across this plugin. http://svgimporter.com/
    It looks quite promising. The developer claims that you would just have to drag and drop your SVG files like unity sprites. But it generates meshes more likely as your script does.

  • MarryU says:

    I don’t see many comments here, it means you have low visitors. I know how to make your website go viral. If you want to know just search in google for:
    Kelashy’s method to go viral

  • Tim says:

    This doesn’t appear to work with most SVG files. Simple shapes throw errors and even slightly edited versions of the included examples won’t load anymore.

Leave a Reply

Your email address will not be published. Required fields are marked *


*

Copyright © 2011-2017 virtualPlayground All rights reserved.
VP based on Desk Mess Mirrored v1.8.3 theme from BuyNowShop.com.