Changing the order of the layers with Python

I tried to change the order of the layers within python, but since the Layer object is neither an array neither a dictionary but a <objective-c class GSLayer at 0x10fbde728> I don’t know how to do. It seems like I can’t use python function to sort the layers?

How to change the order of the layers programatically? (For example send layer[4] to layer[1]?
The only way I can think of is copying the element in a specific order to then delete the old one.
There has to be a better way to do it?

(I try to do this for a color font)

This should get you started. I just quickly wrote this, you need to implement some index checking (to avoid out of bounds errors) and also to which master the layers belong to, probably.

newIndex = 0 # Layer index to be inserted to
oldIndex = 3 # Layer index to be moved
layers = Layer.parent.layers # get the layerProxy
layers.insert(newIndex, layers[oldIndex]) # change the order
Layer.parent.layers = layers # actually apply the changed order

It weirdly seems to not need the previous layer to be removed (for example with layers.pop(oldIndex), which baffles me, as well as for some reason this snipped rearranges the layers, but not as expected, I cannot get the first (non-master) layer to be exchanged. Anyway it could still get you started.

1 Like

Thanks for the input!

It seems like a lot of things are happening in the back, and I don’t really get the logic of it…
For example if I don’t apply the change all the layers are removed from the list? Weird.
I’ll try to understand the logic, but I feel like I’m missing some informations to get it.
I’ll let you know if I manage to make it work.

One thing to notice, if you call for the layers of the glyphs, you don’t get a default python list, but a GSLayerProxy as the object. Apparently you can do things with that like insert, or remove or add items, but those methods are not applied to the layers list right away (which is good, because you cannot iterate over an array and change it at the same time). That is why you then have to apply the changed layerProxy to be the new set of layers the glyph has.

I think

The masters layers can’t be reorder just like that. You need to make it a master layer.

For the other layers, the layer proxy is not meant to be able to allow to order stuff. You would need to fall back to the native .layers implementation (I‘ll need to put together some sample code if you need it).


Ok I’m not sure to understand. What do you mean by using the native .layers implementation? Using Obj C instead of python?

Normally you interact with the python wrapper. The native API is a not a pretty but sometime you can do more. Both can be accessed from python.

Can you explain what exactly you are trying to do?

I converted a colour font from a layer font but the order of my layers is wrong.
As a result some elements that should be on top are covered by bigger ones that should be in the back.

If I could reposition layers as I wish like in a dictionary or an array (send [1] to [4] for example) I could write a script to reorder them based on there titles.

Plus now I’m very curious about this Python-ObjC native API!

Have a look at the mekkablue > Color Font > Convert… script. You should find good code samples in there.