Search code examples
node.jssvglayeradobe-illustratorpaperjs

paper.js & Adobe Illustrator SVG : layers compatibilty


I am creating SVG files using paper.js (from node.js, with the paper-jsdom package), and I would like to make them as compliant as possible with Adobe Illustrator. In order to do so, I am trying to repoduce the steps described [here]. But then, exporting into SVG using the exportSVG function, I get something quite different :

Both shapes are in the same layer, but in different groups

The layer compatibility between paper.js and AI does not seems to work anymore. So, am I missing something here ? Is it because of my version of AI (CC 2018) ? Would there be a way to bypass this issue ?


Solution

  • I don't think that Paper.js SVG export was ever compatible with Illustrator layer model.
    You say that this "does not seems to work anymore" but did you make it work with previous versions of Paper.js/AI ?
    If not, I guess that you were confused by the analogy that is made in Paper.js documentation about their shared layer concept.
    But this analogy is only made because users are used to AI layers and this allow them to better understand how Paper.js works.

    From that, I was curious to see how AI was able to restore its layers after a SVG export, to see if there was a possible workaround in your case.
    When you export your AI project as SVG, you can choose to "Preserve Illustrator Editing Capabilities" or not.
    If you don't, the exported SVG will look like this:

    <?xml version="1.0" encoding="utf-8"?>
    <!-- Generator: Adobe Illustrator 17.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
    <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN"
        "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
    <svg version="1.0" id="Calque_1" xmlns="http://www.w3.org/2000/svg"
         xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
         width="1137px" height="937px" viewBox="0 0 1137 937"
         enable-background="new 0 0 1137 937" xml:space="preserve">
    <g id="Calque_1_1_">
        <circle fill="#FF0000" cx="380" cy="238" r="60"/>
    </g>
    <g id="Calque_2">
        <circle fill="#0000FF" cx="569" cy="468" r="60"/>
    </g>
    </svg>
    

    But if you try to load this SVG back into AI, you won't get 2 layers, but only one containing 2 groups (as you do with Paper.js exported SVG).

    If you check "Preserve Illustrator Editing Capabilities", you will get a very different result:

    <?xml version="1.0" encoding="utf-8"?>
    <!-- Generator: Adobe Illustrator 17.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
    <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.0//EN"
        "http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd" [
        <!ENTITY ns_extend "http://ns.adobe.com/Extensibility/1.0/">
        <!ENTITY ns_ai "http://ns.adobe.com/AdobeIllustrator/10.0/">
        <!ENTITY ns_graphs "http://ns.adobe.com/Graphs/1.0/">
        <!ENTITY ns_vars "http://ns.adobe.com/Variables/1.0/">
        <!ENTITY ns_imrep "http://ns.adobe.com/ImageReplacement/1.0/">
        <!ENTITY ns_sfw "http://ns.adobe.com/SaveForWeb/1.0/">
        <!ENTITY ns_custom "http://ns.adobe.com/GenericCustomNamespace/1.0/">
        <!ENTITY ns_adobe_xpath "http://ns.adobe.com/XPath/1.0/">
        ]>
    <svg version="1.0" xmlns:x="&ns_extend;" xmlns:i="&ns_ai;"
         xmlns:graph="&ns_graphs;"
         xmlns="http://www.w3.org/2000/svg"
         xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="1137px"
         height="937px"
         viewBox="0 0 1137 937" enable-background="new 0 0 1137 937"
         xml:space="preserve">
    <switch>
        <foreignObject requiredExtensions="&ns_ai;" x="0" y="0" width="1"
                       height="1">
            <i:pgfRef xlink:href="#adobe_illustrator_pgf">
            </i:pgfRef>
        </foreignObject>
        <g i:extraneous="self">
            <g id="Calque_1">
                <circle fill="#FF0000" cx="380" cy="238" r="60"/>
            </g>
            <g id="Calque_2">
                <circle fill="#0000FF" cx="569" cy="468" r="60"/>
            </g>
        </g>
    </switch>
        <i:pgf id="adobe_illustrator_pgf">
        <![CDATA[
        ...(huge data skipped)
        ]]>
    </i:pgf>
    </svg>
    

    This time, if you load this back into AI, you will get your layers, as expected.
    The difference resides in all the meta data that AI adds to the SVG in order to load it back, and most importantly, the <i:pgf id="adobe_illustrator_pgf"> element.
    There is a thread discussing about the same kind of problem in Inskape context and it seems that this crucial data is a kind of binary data that only AI can read and write.

    So as a final word, unfortunately, I don't think that there is a chance that you or Paper.js can make a SVG file that maps to AI internal layers model.