Global ordering complications with rigged 2D character

Godot Version

Godot Version 4.2.2

Question

Hello!
I have recently made a 2D cutout character with multiple body parts such as upper arms, lower arms, legs and foot etc.

Certain animations increase or decrease the Z value of these cutout sprites.
Here’s the character down below!

The Issue: Turns out the changes I made to the Z index of each part is actually global, meaning ordering issues happen when I make him move behind or on front of another object in the map (FYI, the map uses Y-sort)
Here’s an example when he passes on front of a large box:

As you can see, his left leg and ear draws behind the box because they have negative z values. Similarly if he’s behind the box and a part has a z value > 0 it will draw on front of the box which is undesirable.

So I help to figure out how to make the Z index changes I made within the character to only affect ordering within the character please!
Or at the very least, a way to display the whole character as a single image if that’s not possible.

Note: I already tried to make use of the RenderingServer.canvas_item_set_draw_index() function instead of using Z values to order the limbs, but it isn’t ideal for my situation. This is because canvas_item_set_draw_index orders only among sibling nodes, which means I would not be able to have a child node draw over a sibling of it’s parent (Example, if I wanted the upper arm to draw behind the torso but the hand – a child of the upper arm – to draw above it, I wouldn’t be able to with this structure)

Have you tried messing around with the Z as relative value?

I did try that, but the relative z-index checkbox doesn’t help the issue.
Documentation explanation below!
If true, the node’s Z index is relative to its parent’s Z index. If this node’s Z index is 2 and its parent’s effective Z index is 3, then this node’s effective Z index will be 2 + 3 = 5.
So sadly that button doesn’t stop the children of a node to stop interfering with other objects globally :sob:

I might seem dumb, but why can’t you just increase the parent Z, it should just bring the entire character to the front of other objects. What about using Top level? Sorry if I can’t help you :frowning:
Beautiful character though

Yo! To anyone who may come across this issue in the future incase you are making a top down game with cutout animations, I found a way around it!

first, put all of the sprites that make up the character in the same level in the tree, then connect the bones you have to their respective sprites using RemoteTransform2D nodes.
This way you can make use of set_draw_index() while still having the sprites move with the bones.
If you ever want to change the ordering within animations, just write a function in your character script to do that and call it from an animation track.

Hope this helps someone.

1 Like

hey im having the same problem, im using layered sprites without a skeleton though. could you tell me where exactly you found this set_draw_index() function and what node its from, i cant seem to find any info on it but it sounds exactly like what i need.

Hi! set_draw_index() isn’t a property (at least, I haven’t seen it in the editor ever).
You can only change it from code unfortunately.
You can see the documentation for it here
RenderingServer.canvas_item_set_draw_index(Node you want, Integer layer)

I personally made a function that takes in an array of nodes and integers to mass change these indexes when needed by calling the function from an animation track. Good luck with whatever you end up doing!

2 Likes

thanks for the info, i tried a bunch but couldnt get that draw index function to work. seems a bit too low level anyway to mess with that. ill be making some function that changes the node order between siblings since that changes which gets drawn first. thanks anyway and good luck on your project!