bevy icon indicating copy to clipboard operation
bevy copied to clipboard

Should EntityCommands consume self?

Open Luminoth opened this issue 6 months ago • 2 comments

Bevy version

0.14.1

What you did

This is more of a question about a possible change than a real Bug bug - I'm wondering if EntityCommands should consume self rather than taking it in as a reference and returning it as a reference. The way it works today, you can't do something like this:

fn create_button<'a>(parent: &'a mut ChildBuilder) -> EntityCommands<'a> {
    parent
        .spawn(ButtonBundle::default())
        .with_children(|parent| {
            parent.spawn(TextBundle::default());
        })
}

because spawn creates a temporary that can't be returned from here. A key to this is that the method is taking in a ChildBuilder, not a Commands, implying that it's being used from within a call to with_children. Normally a method like this might return the Entity instead and then the caller would use Commands to further modify it, but that isn't possible here:

    commands
        .spawn(ButtonBundle::default())
        // this fails to build because commands is being held mutably in the outer call to spawn
        // and can't be accessed within the closure
        .with_children(|parent| {
            let ent = parent.spawn(TextBundle::default()).id();
            commands.entity(ent).insert(TextBundle::default());
        });

Not being able to do this makes composing more complex, reusable UI structures somewhat difficult I think and I believe making the change to have those EntityCommands methods consume and return self would fix that without breaking anything else?

I've also tried resolving this by returning from create_button with reborrow but it appears to still be referencing the temporary created by the call to parent.spawn() and so fails the same as the original version

Luminoth avatar Aug 22 '24 22:08 Luminoth