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

Unify picking backends #17348

Merged
merged 13 commits into from
Mar 18, 2025
Merged

Conversation

chompaa
Copy link
Member

@chompaa chompaa commented Jan 13, 2025

Objective

Currently, our picking backends are inconsistent:

  • Mesh picking and sprite picking both have configurable opt in/out behavior. UI picking does not.
    • Sprite picking uses SpritePickingCamera and Pickable for control, but mesh picking uses RayCastPickable.
  • MeshPickingPlugin is not a part of DefaultPlugins. SpritePickingPlugin and UiPickingPlugin are.

Solution

  • Add configurable opt in/out behavior to UI picking (defaults to opt out).
  • Replace RayCastPickable with MeshPickingCamera and Pickable.
  • Remove SpritePickingPlugin and UiPickingPlugin from DefaultPlugins.

Testing

Ran some examples.

Migration Guide

UiPickingPlugin and SpritePickingPlugin are no longer included in DefaultPlugins. They must be explicitly added.

RayCastPickable has been replaced in favor of the MeshPickingCamera and Pickable components. You should add them to cameras and entities, respectively, if you have MeshPickingSettings::require_markers set to true.

@chompaa chompaa added X-Contentious There are nontrivial implications that should be thought through D-Modest A "normal" level of difficulty; suitable for simple features or challenging fixes S-Needs-Review Needs reviewer attention (from anyone!) to move forward A-Picking Pointing at and selecting objects of all sorts labels Jan 13, 2025
@alice-i-cecile alice-i-cecile added M-Needs-Release-Note Work that should be called out in the blog due to impact M-Needs-Migration-Guide A breaking change to Bevy's public API that needs to be noted in a migration guide labels Jan 13, 2025
@alice-i-cecile alice-i-cecile added this to the 0.16 milestone Jan 13, 2025
@alice-i-cecile
Copy link
Member

@notmd @fjkorf can I get your reviews over here? I'd like to unify all this for 0.16.

@alice-i-cecile alice-i-cecile removed the M-Needs-Release-Note Work that should be called out in the blog due to impact label Feb 24, 2025
@chompaa chompaa force-pushed the unify-picking-backends branch from eb6d2a7 to ec411bd Compare February 25, 2025 00:12
Copy link
Contributor

@fjkorf fjkorf left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These changes make sense to me. The naming is more consistent. I appreciate the extra comments scattered throughout. I'm not sure if it makes sense to leave picking out of the default plugins, but I don't think either option is bad. I was able to run this code locally and try the examples. All said this looks good to me.

Comment on lines +171 to +172
if settings.require_markers && node.pickable.is_none() {
continue;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we should not make picking opt-out with require_markers. Maybe introduce a second flag or remove configurable opt-out. The require_markers should only use to config the camera, not the UI elements picking opt-in/out

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe introduce a second flag

To me, this would decrease readability for opt-in behavior. In my opinion, if you opt-in, you are opting to be explicit, so not having to add UiPickingCamera when all your UI needs Pickable seems off. Happy to hear your thoughts though :)

[...] or remove configurable opt-out

To the best of my knowledge UI picking is going to drive a lot of the interactions going forward, so I think it makes sense to be opt-out by default (and consequently have the option to opt-in since there's no (?) perf loss).

Copy link
Contributor

@notmd notmd Feb 25, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi, sorry for not making it clear. I mean a common scenario is you start with picking opt-out (all elements are pickable without inserting Pickable) and 1 camera. Then you start adding more cameras and now want to disable picking for them. You starting set make require_markers to true, but this will regret (even if you make your main camera to allow picking by inserting UiPickingCamera) all UI elements you have before because now it requires to explicit to insert Pickable. For UI, I only want to insert Pickable when I want to custom the behavior of Pickable. The only reason for UI picking opt-in is performance, but I believe you will soon realize that the performance gain is not worth the DX.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think renaming the flag inside of UIPickingSettings to something more explicit like only_pickable is reasonable.

That said the reason for making picking opt-in is performance, and that performance gain is worth a learning moment in the developer experience. The DX of updating your UI to reflect your picking preferences does not seem onerous.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we should remove the ability to toggle opt-out behavior at the plugin level, and then use required components as needed to get "automatic picking". We don't need more mechanisms for this! I also think that the UiPickingPlugin should be added as part of UiPlugin.

Copy link
Member Author

@chompaa chompaa Feb 27, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Right, that makes sense, I agree required components do solve the DX issue. How do we want to handle it for cameras though? I feel like having the plugin level toggle is nice in this case. I can see why UiPickingPlugin should be added as a part of UiPlugin, but I'm not sure I agree with SpritePickingPlugin being added by default. What's the consensus there? If we decide that SpritePickingPlugin be added by default then I think MeshPickingPlugin should be too.

Edit: MeshPickingPlugin will need to be considered too.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think no SpritePickingPlugin by default; it's definitely feasible to write games that never use it. The same cannot be said for building UIs that don't!

Not sure on the camera config TBH 🤔

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think sprite picking and ui picking should be enabled by default. Sprite picking has almost no cost associated with it (per-entity opt-in, filtered out cheaply via archetype queries) and provides high utility, and UI picking is a core piece of the UI puzzle.

@notmd
Copy link
Contributor

notmd commented Feb 25, 2025

About the SpritePickingPlugin and UiPickingPlugin can we add it directly to the DefaultPlugins?. I agree removing them from SpritePlugin and UiPlugin, but many other plugins are doing the same.

Copy link
Contributor

@NthTensor NthTensor left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks fine to me. Cart's suggestion to enable ui and sprite picking by default is still outstanding, but we have a release candidate to cut, and I'd like this to be in there from the start.

I propose we merge this, spin out the remaining few work items, and do some small refinements during the RC.

@alice-i-cecile alice-i-cecile added S-Ready-For-Final-Review This PR has been approved by the community. It's ready for a maintainer to consider merging it and removed S-Needs-Review Needs reviewer attention (from anyone!) to move forward labels Mar 18, 2025
@alice-i-cecile alice-i-cecile added S-Needs-Review Needs reviewer attention (from anyone!) to move forward and removed S-Ready-For-Final-Review This PR has been approved by the community. It's ready for a maintainer to consider merging it labels Mar 18, 2025
@@ -181,6 +180,7 @@ impl Plugin for UiPlugin {
)
.chain(),
)
.add_plugins(UiPickingPlugin)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is not gated on the feature flag, which is inconsistent with the sprite picking backend and also seems necessary for configuration.

DefaultPlugins,
InputDispatchPlugin,
TabNavigationPlugin,
UiPickingPlugin,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is no longer necessary, as it is provided by default. The other examples touched by this PR should also be updated to remove the now-spurious registrations.

@alice-i-cecile alice-i-cecile added this pull request to the merge queue Mar 18, 2025
Merged via the queue into bevyengine:main with commit 65e289f Mar 18, 2025
33 checks passed
mockersf pushed a commit that referenced this pull request Mar 18, 2025
# Objective

Currently, our picking backends are inconsistent:

- Mesh picking and sprite picking both have configurable opt in/out
behavior. UI picking does not.
- Sprite picking uses `SpritePickingCamera` and `Pickable` for control,
but mesh picking uses `RayCastPickable`.
- `MeshPickingPlugin` is not a part of `DefaultPlugins`.
`SpritePickingPlugin` and `UiPickingPlugin` are.

## Solution

- Add configurable opt in/out behavior to UI picking (defaults to opt
out).
- Replace `RayCastPickable` with `MeshPickingCamera` and `Pickable`.
- Remove `SpritePickingPlugin` and `UiPickingPlugin` from
`DefaultPlugins`.

## Testing

Ran some examples.

## Migration Guide

`UiPickingPlugin` and `SpritePickingPlugin` are no longer included in
`DefaultPlugins`. They must be explicitly added.

`RayCastPickable` has been replaced in favor of the `MeshPickingCamera`
and `Pickable` components. You should add them to cameras and entities,
respectively, if you have `MeshPickingSettings::require_markers` set to
`true`.

---------

Co-authored-by: Alice Cecile <[email protected]>
github-merge-queue bot pushed a commit that referenced this pull request Mar 18, 2025
# Objective

@cart noticed some issues with my work in
#17348 (comment),
which I somehow missed before merging the PR.

## Solution

- feature gate the UiPickingPlugin correctly
- don't manually add the picking plugins

## Testing

Ran the debug_picking and sprite_picking examples (for UI and sprites
respectively): both seem to work fine.
mockersf pushed a commit that referenced this pull request Mar 18, 2025
# Objective

@cart noticed some issues with my work in
#17348 (comment),
which I somehow missed before merging the PR.

## Solution

- feature gate the UiPickingPlugin correctly
- don't manually add the picking plugins

## Testing

Ran the debug_picking and sprite_picking examples (for UI and sprites
respectively): both seem to work fine.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-Picking Pointing at and selecting objects of all sorts D-Modest A "normal" level of difficulty; suitable for simple features or challenging fixes M-Needs-Migration-Guide A breaking change to Bevy's public API that needs to be noted in a migration guide S-Needs-Review Needs reviewer attention (from anyone!) to move forward X-Contentious There are nontrivial implications that should be thought through
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants