# How to control layers when exporting an SVG

**URL:** <https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758>\
**Category:** Processing.py\
**Created:** [June 11, 2020, 2:56am UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758 "2020-06-11T02:56:49Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![slashwreck](https://avatars.discourse-cdn.com/v4/letter/s/90db22/32.png) [@slashwreck](https://discourse.processing.org/u/slashwreck)\
**Post date:** [June 11, 2020, 2:56am UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758/1 "2020-06-11T02:56:49Z")

</div>

![desert_layers](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/2X/2/27ff1de3aa2f430f2a4e6cc088ca814cf5b0262e.png)

I export an SVG from Processing, load into Inkscape, and then send to my AxiDraw. I would like to separate the image into three separate layers, RGB, or CMY in the exported SVG. This will allow me to print different layers with different pens on my axiDraw.

Is there any way to control the hierarchy of objects/layers in the processing canvas that gets sent to SVG? Right now processing seems to throw everything under level or two of ‘subdirectory’ (don’t know the right term) . Would be nice if i could maybe use "`beginShape()` `endShape()`" with some parameters to isolate tranches of `curveVertex()` so that they are segregated meaningfully rather than simply order-of-creation.

---

<div class="post-metadata">

**Author:** ![slashwreck](https://avatars.discourse-cdn.com/v4/letter/s/90db22/32.png) [@slashwreck](https://discourse.processing.org/u/slashwreck)\
**Post date:** [June 11, 2020, 5:44am UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758/2 "2020-06-11T05:44:04Z")

</div>

![image](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/2X/f/ff3cca5b91b453e1cb51e379d69e1849f971b91c.png)

I thought maybe I could nest `beginShape()` and `endShape()` statements to get a nested object layers. Alas, no, it gave me a wierd subdirectory structure and a bunch of objects that were blank (highlighted in red)

> add\_library(“svg”)
> 
> def settings():
> 
> ```
> #size(300,300)
> FN="foo.svg"
> size(300,300, SVG, FN)
> 
> ```
> 
> def setup():  
> noLoop()
> 
> def draw():
> 
> ```
> beginShape()
> circle(20,20,10)
> endShape()
> 
> beginShape()
> circle(50,50,10)
> endShape()
> 
> beginShape()
> beginShape()
> circle(80,80,10)
> endShape()
> beginShape()
> circle(90,90,10)
> endShape()
> endShape()
> print("done")
> 
> ```

---

<div class="post-metadata">

**Author:** ![tabreturn](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/tabreturn/32/3697_2.png) [@tabreturn](https://discourse.processing.org/u/tabreturn)\
**Post date:** [June 11, 2020, 6:07am UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758/3 "2020-06-11T06:07:16Z")

</div>

How about trying separate SVG files? Something like –

```auto
beginRecord(SVG, 'circles.svg')
circle(100, 100, 50)
circle(200, 100, 50)
endRecord()

beginRecord(SVG, 'squares.svg')
square(100, 300, 50)
square(200, 300, 50)
endRecord()

```

You can then open the SVGs in a text editor and combine them, defining your own group (`<g>`) tags. Or, automate this process using Python’s [`xml.etree`](https://docs.python.org/2.7/library/xml.etree.elementtree.html) module.

---

<div class="post-metadata">

**Author:** ![tabreturn](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/tabreturn/32/3697_2.png) [@tabreturn](https://discourse.processing.org/u/tabreturn)\
**Post date:** [June 11, 2020, 7:33am UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758/4 "2020-06-11T07:33:59Z")

</div>

To add to my previous response, here’s an `xml.etree` example:

```auto
add_library('svg')
# xml.etree module
from xml.etree import ElementTree

svgs = ['circles.svg', 'squares.svg']

# create a circles.svg and draw circles in it
beginRecord(SVG, svgs[0])
fill('#FF0000')
circle(10, 10, 10)
circle(50, 10, 10)
endRecord()

# create a squares.svg and draw squares in it
beginRecord(SVG, svgs[1])
fill('#0000FF')
square(10, 30, 10)
square(50, 30, 10)
endRecord()

# create an empty combined.svg file
beginRecord(SVG, 'combined.svg'); endRecord()
ElementTree.register_namespace('', 'http://www.w3.org/2000/svg')
tree = ElementTree.parse('combined.svg')
combined = tree.getroot()

# add the (circles/squares) svgs to the combined.svg file
for svg in svgs:
    file = ElementTree.parse(svg).getroot()
    group = ElementTree.SubElement(combined, 'g')
    group.set('id', svg)
    for child in file.getchildren():
        group.append(child)

# save the changes to the combined.svg file
tree.write('combined.svg')

```

---

<div class="post-metadata">

**Author:** ![slashwreck](https://avatars.discourse-cdn.com/v4/letter/s/90db22/32.png) [@slashwreck](https://discourse.processing.org/u/slashwreck)\
**Post date:** [June 13, 2020, 12:47pm UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758/5 "2020-06-13T12:47:27Z")

</div>

> [@tabreturn](#):
>
> ```auto
> add_library('svg')
> # xml.etree module
> from xml.etree import ElementTree
> 
> svgs = ['circles.svg', 'squares.svg']
> 
> # create a circles.svg and draw circles in it
> beginRecord(SVG, svgs[0])
> fill('#FF0000')
> circle(10, 10, 10)
> circle(50, 10, 10)
> endRecord()
> 
> # create a squares.svg and draw squares in it
> beginRecord(SVG, svgs[1])
> fill('#0000FF')
> square(10, 30, 10)
> square(50, 30, 10)
> endRecord()
> 
> # create an empty combined.svg file
> beginRecord(SVG, 'combined.svg'); endRecord()
> ElementTree.register_namespace('', 'http://www.w3.org/2000/svg')
> tree = ElementTree.parse('combined.svg')
> combined = tree.getroot()
> 
> # add the (circles/squares) svgs to the combined.svg file
> for svg in svgs:
> file = ElementTree.parse(svg).getroot()
> group = ElementTree.SubElement(combined, 'g')
> group.set('id', svg)
> for child in file.getchildren():
> group.append(child)
> 
> # save the changes to the combined.svg file
> tree.write('combined.svg')
> 
> ```

Wow, this is a great headstart, Thank you.

A question about the result (viewed in Inkscape). Somehow Inkscape sees the various layers as sudirectories of objects in the `Objects` pane. However, it sees nothing in the `Layers` pane. I don’t understand this behavior. Because even the icon for the ‘subdirectory’ `squares.svg`, I can right-click and it offers me the option to `rename layer`. So it quacks like Layer and looks like a Layer, but Inkscape doesn’t call it a Layer in the `layers` pane.

This isn’t pedantic issue – I have an inkscape plugin for my AxiDraw that allows me to print by specific layer name. Since there are no listings in the layer pane, I cannot use that Axidraw plugin plot-by-layers functionality.

Very easily could be something I fundamentally misunderstand with Inkscape…

 ![image](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/2X/5/52fdd77fc53655276fa69d2a60b37190ec973202.png)

 ![image](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/2X/1/1247fb21c204f72525f30ddaac5a03fffb965057.png)

---

<div class="post-metadata">

**Author:** ![tabreturn](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/tabreturn/32/3697_2.png) [@tabreturn](https://discourse.processing.org/u/tabreturn)\
**Post date:** [June 13, 2020, 9:50pm UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758/6 "2020-06-13T21:50:24Z")

</div>

Inkscape adds its own embellishments to the standard SVG format, including attributes to define layers. Add these two `inkscape:`-prefixed attributes to your Processing code:

```auto
    ...
    group.set('id', svg)
    group.set('inkscape:groupmode', 'layer')
    group.set('inkscape:label', svg)
    ...

```

BTW, I’m in the process of ordering an AxiDraw (A3) right now. Thanks to you, I’m learning how it works before I’ve even got my hands on it 😃

---

<div class="post-metadata">

**Author:** ![slashwreck](https://avatars.discourse-cdn.com/v4/letter/s/90db22/32.png) [@slashwreck](https://discourse.processing.org/u/slashwreck)\
**Post date:** [June 14, 2020, 1:05am UTC](https://discourse.processing.org/t/how-to-control-layers-when-exporting-an-svg/21758/7 "2020-06-14T01:05:43Z")

</div>

Yeah, that fixed it perfectly. This is going to help my workflow immensely. Thanks

I found a handful of tutorials on SVG at the [bottom](https://inkscape.org/develop/about-svg/) – are there any other resources you suggest to understand the details of svg?

Yeah, I’ve coveted an AxiDraw for many years and at times was tempted to just buy a cheap aliexpress clone. They’re not cheap and I wasn’t keen to learn a new toolchain. Covid cancelled my vacation, so I used that money to buy an SE/A3. Really glad I bought the AxiDraw – the fit and finish, not only of the machine, but all the supporting documentation, is amazing. I’ve never read such refined documentation. The inkscape plugin works well, and Oskay seems to answer support queries on Discord at any moment of the day.

I would recommend:

1. buying extra pen-lift servos. They’re cheap, easy to replace, and will fail when it’s least convenient. (they’re a slow-motion disposable part)
2. buying the magnetic easel. These are flatter, stiffer, and hold the paper more easily, especially weird-shapes, than the particle board thing that comes stock.
3. potentially buy the pen rotation stage and the XL pen clip if you want to print with weird markers, etc.
