Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

UI button is still Interaction::Pressed when to the right of its Overflow::clip() parent. #10668

Closed
Selene-Amanita opened this issue Nov 21, 2023 · 4 comments
Labels
A-UI Graphical user interfaces, styles, layouts, and widgets C-Bug An unexpected or incorrect behavior

Comments

@Selene-Amanita
Copy link
Member

Selene-Amanita commented Nov 21, 2023

Bevy version

0.12.0

What you did

Try to make a Carroussel, here is a simplified version with a root node (with purple border) that hides the overflow, a stip node just underneath, and three item children (red, blue and green background) that can be clicked. The strip is setup to display the middle child, green.

image

use bevy::prelude::*;

fn main() {
    App::new()
        .add_plugins(DefaultPlugins)
        .add_systems(Startup, setup)
        .add_systems(Update, interact_check)
        .run();
}

fn setup(mut commands: Commands) {
    commands.spawn(Camera2dBundle::default());

    commands.spawn(NodeBundle {
        style: Style {
            position_type: PositionType::Absolute,
            width: Val::Px(220.),
            height: Val::Px(220.),
            left: Val::Px(300.),
            top: Val::Px(300.),
            border: UiRect::all(Val::Px(10.)),
            overflow: Overflow::clip(),
            ..default()
        },
        border_color: BorderColor(Color::PURPLE),
        ..default()
    }).with_children(|parent| {
        parent.spawn(NodeBundle {
            style: Style {
                position_type: PositionType::Absolute,
                width: Val::Px(600.),
                height: Val::Px(200.),
                left: Val::Px(-200.),
                ..default()
            },
            ..default()
        }).with_children(|parent| {
            parent.spawn(ButtonBundle {
                style: Style {
                    width: Val::Px(200.),
                    height: Val::Px(200.),
                    ..default()
                },
                background_color: BackgroundColor(Color::RED),
                ..default()
            });
            parent.spawn(ButtonBundle {
                style: Style {
                    width: Val::Px(200.),
                    height: Val::Px(200.),
                    ..default()
                },
                background_color: BackgroundColor(Color::GREEN),
                ..default()
            });
            parent.spawn(ButtonBundle {
                style: Style {
                    width: Val::Px(200.),
                    height: Val::Px(200.),
                    ..default()
                },
                background_color: BackgroundColor(Color::BLUE),
                ..default()
            });
        });
    });
}

fn interact_check(
    interactions: Query<(&Interaction, &BackgroundColor), Changed<Interaction>>
) {
    for (interaction, background_color) in interactions.iter() {
        if matches!(interaction, Interaction::Pressed) {
            dbg!(format!("Pressed {:?}", background_color.0));
        }
    }
}

What went wrong

  • When I click in the left area outside of the root node, nothing happens, as expected, the Interaction component of the first red item doesn't change to Pressed, this is expected
  • When I click in the right area outside of the root node, to the right, the Interaction of the third blue item changes to Pressed, I feel like it shouldn't
  • I would expect the left and right border of the root node to appear in purple, instead it is "overiden" by the children nodes
  • When I click on the red and blue children's area that overlap the border of the root node, their Interaction component changes to Pressed, I feel like it shouldn't.

image

@Selene-Amanita Selene-Amanita added C-Bug An unexpected or incorrect behavior S-Needs-Triage This issue needs to be labelled A-UI Graphical user interfaces, styles, layouts, and widgets and removed S-Needs-Triage This issue needs to be labelled labels Nov 21, 2023
@hymm
Copy link
Contributor

hymm commented Nov 21, 2023

Does #10454 fix this issue for you?

@Selene-Amanita
Copy link
Member Author

Selene-Amanita commented Nov 21, 2023

@hymm

It does fix the "clicking in the right area outside of the root node" part, which is the most annoying and wrong one, and the reason I wrote this issue.

It doesn't fix the weird interactions with the borders though, so I will probably keep this open for that reason.

Thank you for linking it!

@Selene-Amanita Selene-Amanita changed the title UI button is still Interaction::Pressed when to the right of it's Overflow::clip() parent. UI button is still Interaction::Pressed when to the right of its Overflow::clip() parent. Nov 21, 2023
@ickshonpe
Copy link
Contributor

ickshonpe commented Nov 22, 2023

The interactions with the borders are correct.
In your example, the border belongs to the node with Overflow::clip applied to it. The border is within the clipped area and so anything visible is drawn above it.

Instead, you need to change the border so it's around and not inside the node with clipping. I modified your example to what I think is the desired behaviour:

use bevy::prelude::*;

fn main() {
    App::new()
        .add_plugins(DefaultPlugins)
        .add_systems(Startup, setup)
        .add_systems(Update, interact_check)
        .run();
}

fn setup(mut commands: Commands) {
    commands.spawn(Camera2dBundle::default());

    commands.spawn(NodeBundle {
        style: Style {
            position_type: PositionType::Absolute,
            left: Val::Px(300.),
            top: Val::Px(300.),
            border: UiRect::all(Val::Px(10.)),
            ..Default::default()
        },
        border_color: BorderColor(Color::PURPLE),
        ..Default::default()
    }).with_children(|parent| {
        parent.spawn(NodeBundle {
            style: Style {
                width: Val::Px(200.),
                height: Val::Px(200.),    
                overflow: Overflow::clip(),
                ..default()
            },
            ..default()
        }).with_children(|parent| {
            parent.spawn(NodeBundle {
                style: Style {
                    position_type: PositionType::Absolute,
                    width: Val::Px(600.),
                    height: Val::Px(200.),
                    left: Val::Px(-200.),
                    ..default()
                },
                ..default()
            }).with_children(|parent| {
                parent.spawn(ButtonBundle {
                    style: Style {
                        width: Val::Px(200.),
                        height: Val::Px(200.),
                        ..default()
                    },
                    background_color: BackgroundColor(Color::RED),
                    ..default()
                });
                parent.spawn(ButtonBundle {
                    style: Style {
                        width: Val::Px(200.),
                        height: Val::Px(200.),
                        ..default()
                    },
                    background_color: BackgroundColor(Color::GREEN),
                    ..default()
                });
                parent.spawn(ButtonBundle {
                    style: Style {
                        width: Val::Px(200.),
                        height: Val::Px(200.),
                        ..default()
                    },
                    background_color: BackgroundColor(Color::BLUE),
                    ..default()
                });
            });
        });
    });
}

fn interact_check(
    interactions: Query<(&Interaction, &BackgroundColor), Changed<Interaction>>
) {
    for (interaction, background_color) in interactions.iter() {
        if matches!(interaction, Interaction::Pressed) {
            dbg!(format!("Pressed {:?}", background_color.0));
        }
    }
}

@Selene-Amanita
Copy link
Member Author

@ickshonpe I see, I didn't know that was expected behavior.

I will close this as a non-issue/duplicate of #10470 then.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-UI Graphical user interfaces, styles, layouts, and widgets C-Bug An unexpected or incorrect behavior
Projects
None yet
Development

No branches or pull requests

3 participants