Add removal_detection example (#945)

Co-authored-by: Carter Anderson <mcanders1@gmail.com>
This commit is contained in:
Lukas Orsvärn 2020-11-30 22:25:49 +01:00 committed by GitHub
parent f35f813137
commit d9c428e32c
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 85 additions and 0 deletions

View file

@ -10,6 +10,7 @@ current changes on git with [previous release tags][git_tag_comparison].
## Unreleased
### Added
- [`bevy_log`][836]
- Adds logging functionality as a Plugin.
- Changes internal logging to work with the new implementation.
@ -21,7 +22,10 @@ current changes on git with [previous release tags][git_tag_comparison].
- [Added `set_cursor_position` to `Window`][917]
- [Added new Bevy reflection system][926]
- Replaces the properties system
- [Add removal_detection example][945]
### Changed
- [FileAssetIo includes full path on error][821]
- [Removed ECS query APIs that could easily violate safety from the public interface][829]
- [Changed Query filter API to be easier to understand][834]
@ -33,7 +37,9 @@ current changes on git with [previous release tags][git_tag_comparison].
- Created getters to get `Time` state and made members private.
- Modifying `Time`'s values directly is no longer possible outside of bevy.
- [Use `mailbox` instead of `fifo` for vsync on supported systems][920]
### Fixed
- [Fixed typos in KeyCode identifiers][857]
- [Don't draw text that isn't visible][893]
- [Use `instant::Instant` for WASM compatibility][895]
@ -60,6 +66,7 @@ current changes on git with [previous release tags][git_tag_comparison].
[926]: https://github.com/bevyengine/bevy/pull/926
[931]: https://github.com/bevyengine/bevy/pull/931
[934]: https://github.com/bevyengine/bevy/pull/934
[945]: https://github.com/bevyengine/bevy/pull/945
[955]: https://github.com/bevyengine/bevy/pull/955
## Version 0.3.0 (2020-11-03)

View file

@ -326,6 +326,10 @@ path = "examples/window/multiple_windows.rs"
name = "window_settings"
path = "examples/window/window_settings.rs"
[[example]]
name = "removal_detection"
path = "examples/ecs/removal_detection.rs"
[[example]]
name = "hello_wasm"
path = "examples/wasm/hello_wasm.rs"

View file

@ -0,0 +1,74 @@
// This example shows how you can know when a `Component` has been removed, so you can react to it.
use bevy::prelude::*;
fn main() {
// Information regarding removed `Component`s is discarded at the end of each frame, so you need
// to react to the removal before the frame is over.
//
// Also, `Components` are removed via a `Command`. `Command`s are applied after a stage has
// finished executing. So you need to react to the removal at some stage after the
// `Component` is removed.
//
// With these constraints in mind we make sure to place the system that removes a `Component` on
// the `stage::UPDATE` stage, and the system that reacts on the removal on the
// `stage::POST_UPDATE` stage.
App::build()
.add_plugins(DefaultPlugins)
.add_startup_system(setup.system())
.add_system_to_stage(stage::UPDATE, remove_component.system())
.add_system_to_stage(stage::POST_UPDATE, react_on_removal.system())
.run();
}
// This `Struct` is just used for convenience in this example. This is the `Component` we'll be
// giving to the `Entity` so we have a `Component` to remove in `remove_component()`.
struct MyComponent;
fn setup(
commands: &mut Commands,
asset_server: Res<AssetServer>,
mut materials: ResMut<Assets<ColorMaterial>>,
) {
let texture = asset_server.load("branding/icon.png");
commands
.spawn(Camera2dBundle::default())
.spawn(SpriteBundle {
material: materials.add(texture.into()),
..Default::default()
})
.with(MyComponent); // Add the `Component`.
}
fn remove_component(
time: Res<Time>,
commands: &mut Commands,
query: Query<Entity, With<MyComponent>>,
) {
// After two seconds have passed the `Component` is removed.
if time.seconds_since_startup() > 2.0 {
if let Some(entity) = query.iter().next() {
commands.remove_one::<MyComponent>(entity);
}
}
}
fn react_on_removal(
mut materials: ResMut<Assets<ColorMaterial>>,
query: Query<(Entity, &Handle<ColorMaterial>)>,
) {
// Note: usually this isn't how you would handle a `Query`. In this example it makes things
// a bit easier to read.
let (query_entity, material) = query.iter().next().unwrap();
// `Query.removed<T>` returns an array with the `Entity`s in the `Query` that had its
// `Component` `T` (in this case `MyComponent`) removed at some point earlier during the frame.
for entity in query.removed::<MyComponent>() {
// We compare the `Entity` that had its `MyComponent` `Component` removed with the `Entity`
// in the current `Query`. If they match all red is removed from the material.
if query_entity == *entity {
materials.get_mut(material).unwrap().color.set_r(0.0);
}
}
}