2

I have the following situation:

  • A parent Node, taking all the screen space.
    • A child for the top bar.
    • A child for the game area.
    • A child for the bottom bar.
    • An absolute positioned child for an overlay that must not be bound to the three above.

I can't quite get the above to work, because I can't find a way to define the z-order of the children, at least using the default UiCameraComponents. Here's what I've tried:

  • Adding a Translation component to the absolute positioned child and move it up the Z axis.
  • Giving the absolute positioned child a transform higher up in the Z axis.
  • Spawn the nodes in different orders.

It seems like the overlay child consistently renders behind the relatively positioned siblings.

Cuervo
  • 31
  • 2
  • Can you post a minimum reproducible example? I had a project previously where I managed the z-order via Translation. I would be curious to see what you had and where the failure was. – STF_ZBR Sep 12 '20 at 19:13

2 Answers2

3

Z order in Bevy UI is currently implicitly defined by the hierarchy. Nodes "stack" on top of their parents and on top of siblings that come before them in their parent's children list.

Functionally, z-order is defined using the z translation value of the entity's Transform. For normal sprites you can set this directly. For UI components, there is an underlying system that sets this for you.

Eventually, I would like to make it possible to optionally override Bevy UI's z-order behavior. That should be a matter of adding a new field to "opt out", then allowing people to set the transform's z translation directly.

cart
  • 286
  • 1
  • 3
2

As a workaround for the current stable bevy (0.7), I am using a fixed z for UI nodes.

#[derive(Debug, Component)]
pub(crate) struct UiFixedZ {
    pub z: f32,
}

pub(crate) fn ui_apply_fixed_z(
    mut node_query: Query<(&mut Transform, &mut GlobalTransform, &UiFixedZ), With<Node>>,
) {
    for (mut transform, mut global_transform, fixed) in node_query.iter_mut() {
        transform.translation.z = fixed.z;
        global_transform.translation.z = fixed.z;
    }
}

I am placing the system in the last stage just after the bevy's z-order system.

...
app.add_system_to_stage(CoreStage::Last, ui_apply_fixed_z)
...

when inserting UiFixedZ components keep in mind that you need to take care of all the descendants manually.

...
// inserting with manual z order
.insert(UiFixedZ { z: 101. })
...

   // inserting children with increased z order
   .insert(UiFixedZ { z: 102. })

hope the workaround helps someone. I am personally using it for tooltips. Copied my own comment from github :P


Bevy is young and the situation may change in the future.

tomuxmon
  • 93
  • 1
  • 7