mirror of
https://github.com/bevyengine/bevy
synced 2024-11-22 12:43:34 +00:00
Reorganize SystemParamBuilder docs and examples. (#15102)
# Objective Improve the documentation of `SystemParamBuilder`. Not all builder types have documentation, and the documentation is spread around and not linked together well. ## Solution Reorganize `SystemParamBuilder` docs and examples. All builder types now have their own examples, and the list of builder types is linked from the `SystemParamBuilder` trait. Add some examples to `FilteredEntityRef` and `FilteredEntityMut` so that `QueryParamBuilder` can reference them.
This commit is contained in:
parent
2ec164d279
commit
86e5a5ad9c
4 changed files with 304 additions and 96 deletions
|
@ -4,8 +4,7 @@ use crate::{
|
|||
prelude::QueryBuilder,
|
||||
query::{QueryData, QueryFilter, QueryState},
|
||||
system::{
|
||||
system_param::{DynSystemParam, DynSystemParamState, Local, ParamSet, SystemParam},
|
||||
Query, SystemMeta,
|
||||
DynSystemParam, DynSystemParamState, Local, ParamSet, Query, SystemMeta, SystemParam,
|
||||
},
|
||||
world::{FromWorld, World},
|
||||
};
|
||||
|
@ -13,66 +12,85 @@ use core::fmt::Debug;
|
|||
|
||||
use super::{init_query_param, Res, ResMut, Resource, SystemState};
|
||||
|
||||
/// A builder that can create a [`SystemParam`]
|
||||
/// A builder that can create a [`SystemParam`].
|
||||
///
|
||||
/// ```
|
||||
/// # use bevy_ecs::prelude::*;
|
||||
/// # use bevy_ecs_macros::SystemParam;
|
||||
/// # use bevy_ecs::system::{RunSystemOnce, ParamBuilder, LocalBuilder, QueryParamBuilder};
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct A;
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct B;
|
||||
/// #
|
||||
/// # use bevy_ecs::{
|
||||
/// # prelude::*,
|
||||
/// # system::{SystemParam, ParamBuilder},
|
||||
/// # };
|
||||
/// # #[derive(Resource)]
|
||||
/// # struct R;
|
||||
/// #
|
||||
/// # #[derive(SystemParam)]
|
||||
/// # struct MyParam;
|
||||
/// #
|
||||
/// # let mut world = World::new();
|
||||
/// # world.insert_resource(R);
|
||||
/// #
|
||||
/// fn my_system(res: Res<R>, query: Query<&A>, param: MyParam) {
|
||||
/// // ...
|
||||
/// fn some_system(param: MyParam) {}
|
||||
///
|
||||
/// fn build_system(builder: impl SystemParamBuilder<MyParam>) {
|
||||
/// let mut world = World::new();
|
||||
/// // To build a system, create a tuple of `SystemParamBuilder`s
|
||||
/// // with a builder for each parameter.
|
||||
/// // Note that the builder for a system must be a tuple,
|
||||
/// // even if there is only one parameter.
|
||||
/// (builder,)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(some_system);
|
||||
/// }
|
||||
///
|
||||
/// // To build a system, create a tuple of `SystemParamBuilder`s with a builder for each param.
|
||||
/// // `ParamBuilder` can be used to build a parameter using its default initialization,
|
||||
/// // and has helper methods to create typed builders.
|
||||
/// let system = (
|
||||
/// ParamBuilder,
|
||||
/// ParamBuilder::query::<&A>(),
|
||||
/// ParamBuilder::of::<MyParam>(),
|
||||
/// )
|
||||
/// fn build_closure_system_infer(builder: impl SystemParamBuilder<MyParam>) {
|
||||
/// let mut world = World::new();
|
||||
/// // Closures can be used in addition to named functions.
|
||||
/// // If a closure is used, the parameter types must all be inferred
|
||||
/// // from the builders, so you cannot use plain `ParamBuilder`.
|
||||
/// (builder, ParamBuilder::resource())
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(my_system);
|
||||
///
|
||||
/// // Other implementations of `SystemParamBuilder` can be used to configure the parameters.
|
||||
/// let system = (
|
||||
/// ParamBuilder,
|
||||
/// QueryParamBuilder::new::<&A, ()>(|builder| {
|
||||
/// builder.with::<B>();
|
||||
/// }),
|
||||
/// ParamBuilder,
|
||||
/// )
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(my_system);
|
||||
///
|
||||
/// fn single_parameter_system(local: Local<u64>) {
|
||||
/// // ...
|
||||
/// .build_system(|param, res| {
|
||||
/// let param: MyParam = param;
|
||||
/// let res: Res<R> = res;
|
||||
/// });
|
||||
/// }
|
||||
///
|
||||
/// // Note that the builder for a system must be a tuple, even if there is only one parameter.
|
||||
/// let system = (LocalBuilder(2),)
|
||||
/// fn build_closure_system_explicit(builder: impl SystemParamBuilder<MyParam>) {
|
||||
/// let mut world = World::new();
|
||||
/// // Alternately, you can provide all types in the closure
|
||||
/// // parameter list and call `build_any_system()`.
|
||||
/// (builder, ParamBuilder)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(single_parameter_system);
|
||||
///
|
||||
/// world.run_system_once(system);
|
||||
/// .build_any_system(|param: MyParam, res: Res<R>| {});
|
||||
/// }
|
||||
/// ```
|
||||
///
|
||||
/// See the documentation for individual builders for more examples.
|
||||
///
|
||||
/// # List of Builders
|
||||
///
|
||||
/// [`ParamBuilder`] can be used for parameters that don't require any special building.
|
||||
/// Using a `ParamBuilder` will build the system parameter the same way it would be initialized in an ordinary system.
|
||||
///
|
||||
/// `ParamBuilder` also provides factory methods that return a `ParamBuilder` typed as `impl SystemParamBuilder<P>`
|
||||
/// for common system parameters that can be used to guide closure parameter inference.
|
||||
///
|
||||
/// [`QueryParamBuilder`] can build a [`Query`] to add additional filters,
|
||||
/// or to configure the components available to [`FilteredEntityRef`](crate::world::FilteredEntityRef) or [`FilteredEntityMut`](crate::world::FilteredEntityMut).
|
||||
/// You can also use a [`QueryState`] to build a [`Query`].
|
||||
///
|
||||
/// [`LocalBuilder`] can build a [`Local`] to supply the initial value for the `Local`.
|
||||
///
|
||||
/// [`DynParamBuilder`] can build a [`DynSystemParam`] to determine the type of the inner parameter,
|
||||
/// and to supply any `SystemParamBuilder` it needs.
|
||||
///
|
||||
/// Tuples of builders can build tuples of parameters, one builder for each element.
|
||||
/// Note that since systems require a tuple as a parameter, the outer builder for a system will always be a tuple.
|
||||
///
|
||||
/// A [`Vec`] of builders can build a `Vec` of parameters, one builder for each element.
|
||||
///
|
||||
/// A [`ParamSetBuilder`] can build a [`ParamSet`].
|
||||
/// This can wrap either a tuple or a `Vec`, one builder for each element.
|
||||
///
|
||||
/// A custom system param created with `#[derive(SystemParam)]` can be buildable if it includes a `#[system_param(builder)]` attribute.
|
||||
/// See [the documentation for `SystemParam` derives](SystemParam#builders).
|
||||
///
|
||||
/// # Safety
|
||||
///
|
||||
/// The implementor must ensure the following is true.
|
||||
|
@ -97,6 +115,44 @@ pub unsafe trait SystemParamBuilder<P: SystemParam>: Sized {
|
|||
}
|
||||
|
||||
/// A [`SystemParamBuilder`] for any [`SystemParam`] that uses its default initialization.
|
||||
///
|
||||
/// ## Example
|
||||
///
|
||||
/// ```
|
||||
/// # use bevy_ecs::{
|
||||
/// # prelude::*,
|
||||
/// # system::{SystemParam, ParamBuilder},
|
||||
/// # };
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct A;
|
||||
/// #
|
||||
/// # #[derive(Resource)]
|
||||
/// # struct R;
|
||||
/// #
|
||||
/// # #[derive(SystemParam)]
|
||||
/// # struct MyParam;
|
||||
/// #
|
||||
/// # let mut world = World::new();
|
||||
/// # world.insert_resource(R);
|
||||
/// #
|
||||
/// fn my_system(res: Res<R>, param: MyParam, query: Query<&A>) {
|
||||
/// // ...
|
||||
/// }
|
||||
///
|
||||
/// let system = (
|
||||
/// // A plain ParamBuilder can build any parameter type.
|
||||
/// ParamBuilder,
|
||||
/// // The `of::<P>()` method returns a `ParamBuilder`
|
||||
/// // typed as `impl SystemParamBuilder<P>`.
|
||||
/// ParamBuilder::of::<MyParam>(),
|
||||
/// // The other factory methods return typed builders
|
||||
/// // for common parameter types.
|
||||
/// ParamBuilder::query::<&A>(),
|
||||
/// )
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(my_system);
|
||||
/// ```
|
||||
#[derive(Default, Debug, Copy, Clone)]
|
||||
pub struct ParamBuilder;
|
||||
|
||||
|
@ -153,6 +209,45 @@ unsafe impl<'w, 's, D: QueryData + 'static, F: QueryFilter + 'static>
|
|||
}
|
||||
|
||||
/// A [`SystemParamBuilder`] for a [`Query`].
|
||||
/// This takes a closure accepting an `&mut` [`QueryBuilder`] and uses the builder to construct the query's state.
|
||||
/// This can be used to add additional filters,
|
||||
/// or to configure the components available to [`FilteredEntityRef`](crate::world::FilteredEntityRef) or [`FilteredEntityMut`](crate::world::FilteredEntityMut).
|
||||
///
|
||||
/// ## Example
|
||||
///
|
||||
/// ```
|
||||
/// # use bevy_ecs::{
|
||||
/// # prelude::*,
|
||||
/// # system::{SystemParam, QueryParamBuilder},
|
||||
/// # };
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct Player;
|
||||
/// #
|
||||
/// # let mut world = World::new();
|
||||
/// let system = (QueryParamBuilder::new(|builder| {
|
||||
/// builder.with::<Player>();
|
||||
/// }),)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(|query: Query<()>| {
|
||||
/// for _ in &query {
|
||||
/// // This only includes entities with an `Player` component.
|
||||
/// }
|
||||
/// });
|
||||
///
|
||||
/// // When collecting multiple builders into a `Vec`,
|
||||
/// // use `new_box()` to erase the closure type.
|
||||
/// let system = (vec![
|
||||
/// QueryParamBuilder::new_box(|builder| {
|
||||
/// builder.with::<Player>();
|
||||
/// }),
|
||||
/// QueryParamBuilder::new_box(|builder| {
|
||||
/// builder.without::<Player>();
|
||||
/// }),
|
||||
/// ],)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(|query: Vec<Query<()>>| {});
|
||||
/// ```
|
||||
pub struct QueryParamBuilder<T>(T);
|
||||
|
||||
impl<T> QueryParamBuilder<T> {
|
||||
|
@ -229,7 +324,74 @@ unsafe impl<P: SystemParam, B: SystemParamBuilder<P>> SystemParamBuilder<Vec<P>>
|
|||
/// A [`SystemParamBuilder`] for a [`ParamSet`].
|
||||
///
|
||||
/// To build a [`ParamSet`] with a tuple of system parameters, pass a tuple of matching [`SystemParamBuilder`]s.
|
||||
/// To build a [`ParamSet`] with a `Vec` of system parameters, pass a `Vec` of matching [`SystemParamBuilder`]s.
|
||||
/// To build a [`ParamSet`] with a [`Vec`] of system parameters, pass a `Vec` of matching [`SystemParamBuilder`]s.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// # use bevy_ecs::{prelude::*, system::*};
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct Health;
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct Enemy;
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct Ally;
|
||||
/// #
|
||||
/// # let mut world = World::new();
|
||||
/// #
|
||||
/// let system = (ParamSetBuilder((
|
||||
/// QueryParamBuilder::new(|builder| {
|
||||
/// builder.with::<Enemy>();
|
||||
/// }),
|
||||
/// QueryParamBuilder::new(|builder| {
|
||||
/// builder.with::<Ally>();
|
||||
/// }),
|
||||
/// ParamBuilder,
|
||||
/// )),)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(buildable_system_with_tuple);
|
||||
/// # world.run_system_once(system);
|
||||
///
|
||||
/// fn buildable_system_with_tuple(
|
||||
/// mut set: ParamSet<(Query<&mut Health>, Query<&mut Health>, &World)>,
|
||||
/// ) {
|
||||
/// // The first parameter is built from the first builder,
|
||||
/// // so this will iterate over enemies.
|
||||
/// for mut health in set.p0().iter_mut() {}
|
||||
/// // And the second parameter is built from the second builder,
|
||||
/// // so this will iterate over allies.
|
||||
/// for mut health in set.p1().iter_mut() {}
|
||||
/// // Parameters that don't need special building can use `ParamBuilder`.
|
||||
/// let entities = set.p2().entities();
|
||||
/// }
|
||||
///
|
||||
/// let system = (ParamSetBuilder(vec![
|
||||
/// QueryParamBuilder::new_box(|builder| {
|
||||
/// builder.with::<Enemy>();
|
||||
/// }),
|
||||
/// QueryParamBuilder::new_box(|builder| {
|
||||
/// builder.with::<Ally>();
|
||||
/// }),
|
||||
/// ]),)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(buildable_system_with_vec);
|
||||
/// # world.run_system_once(system);
|
||||
///
|
||||
/// fn buildable_system_with_vec(mut set: ParamSet<Vec<Query<&mut Health>>>) {
|
||||
/// // As with tuples, the first parameter is built from the first builder,
|
||||
/// // so this will iterate over enemies.
|
||||
/// for mut health in set.get_mut(0).iter_mut() {}
|
||||
/// // And the second parameter is built from the second builder,
|
||||
/// // so this will iterate over allies.
|
||||
/// for mut health in set.get_mut(1).iter_mut() {}
|
||||
/// // You can iterate over the parameters either by index,
|
||||
/// // or using the `for_each` method.
|
||||
/// set.for_each(|mut query| for mut health in query.iter_mut() {});
|
||||
/// }
|
||||
/// ```
|
||||
pub struct ParamSetBuilder<T>(pub T);
|
||||
|
||||
macro_rules! impl_param_set_builder_tuple {
|
||||
|
@ -302,6 +464,7 @@ unsafe impl<'w, 's, P: SystemParam, B: SystemParamBuilder<P>>
|
|||
}
|
||||
|
||||
/// A [`SystemParamBuilder`] for a [`DynSystemParam`].
|
||||
/// See the [`DynSystemParam`] docs for examples.
|
||||
pub struct DynParamBuilder<'a>(
|
||||
Box<dyn FnOnce(&mut World, &mut SystemMeta) -> DynSystemParamState + 'a>,
|
||||
);
|
||||
|
@ -331,6 +494,23 @@ unsafe impl<'a, 'w, 's> SystemParamBuilder<DynSystemParam<'w, 's>> for DynParamB
|
|||
|
||||
/// A [`SystemParamBuilder`] for a [`Local`].
|
||||
/// The provided value will be used as the initial value of the `Local`.
|
||||
///
|
||||
/// ## Example
|
||||
///
|
||||
/// ```
|
||||
/// # use bevy_ecs::{
|
||||
/// # prelude::*,
|
||||
/// # system::{SystemParam, LocalBuilder, RunSystemOnce},
|
||||
/// # };
|
||||
/// #
|
||||
/// # let mut world = World::new();
|
||||
/// let system = (LocalBuilder(100),)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(|local: Local<usize>| {
|
||||
/// assert_eq!(*local, 100);
|
||||
/// });
|
||||
/// # world.run_system_once(system);
|
||||
/// ```
|
||||
pub struct LocalBuilder<T>(pub T);
|
||||
|
||||
// SAFETY: `Local` performs no world access.
|
||||
|
|
|
@ -99,7 +99,15 @@
|
|||
//! - [`Components`](crate::component::Components) (Provides Components metadata)
|
||||
//! - [`Entities`](crate::entity::Entities) (Provides Entities metadata)
|
||||
//! - All tuples between 1 to 16 elements where each element implements [`SystemParam`]
|
||||
//! - [`ParamSet`]
|
||||
//! - [`()` (unit primitive type)](https://doc.rust-lang.org/stable/std/primitive.unit.html)
|
||||
//!
|
||||
//! In addition, the following parameters can be used when constructing a dynamic system with [`SystemParamBuilder`],
|
||||
//! but will only provide an empty value when used with an ordinary system:
|
||||
//!
|
||||
//! - [`DynSystemParam`]
|
||||
//! - [`Vec<P>`] where `P: SystemParam`
|
||||
//! - [`ParamSet<Vec<P>>`] where `P: SystemParam`
|
||||
|
||||
mod adapter_system;
|
||||
mod builder;
|
||||
|
|
|
@ -606,46 +606,6 @@ unsafe impl<'a, D: ReadOnlyQueryData + 'static, F: QueryFilter + 'static> ReadOn
|
|||
/// }
|
||||
/// # bevy_ecs::system::assert_is_system(event_system);
|
||||
/// ```
|
||||
///
|
||||
/// If you want to use `ParamSet` with a [`SystemParamBuilder`](crate::system::SystemParamBuilder), use [`ParamSetBuilder`](crate::system::ParamSetBuilder) and pass a builder for each param.
|
||||
/// ```
|
||||
/// # use bevy_ecs::{prelude::*, system::*};
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct Health;
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct Enemy;
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct Ally;
|
||||
/// #
|
||||
/// let mut world = World::new();
|
||||
///
|
||||
/// let system = (ParamSetBuilder((
|
||||
/// QueryParamBuilder::new(|builder| {
|
||||
/// builder.with::<Enemy>();
|
||||
/// }),
|
||||
/// QueryParamBuilder::new(|builder| {
|
||||
/// builder.with::<Ally>();
|
||||
/// }),
|
||||
/// ParamBuilder,
|
||||
/// )),)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(buildable_system);
|
||||
/// world.run_system_once(system);
|
||||
///
|
||||
/// fn buildable_system(mut set: ParamSet<(Query<&mut Health>, Query<&mut Health>, &World)>) {
|
||||
/// // The first parameter is built from the first builder,
|
||||
/// // so this will iterate over enemies.
|
||||
/// for mut health in set.p0().iter_mut() {}
|
||||
/// // And the second parameter is built from the second builder,
|
||||
/// // so this will iterate over allies.
|
||||
/// for mut health in set.p1().iter_mut() {}
|
||||
/// // Parameters that don't need special building can use `ParamBuilder`.
|
||||
/// let entities = set.p2().entities();
|
||||
/// }
|
||||
/// ```
|
||||
pub struct ParamSet<'w, 's, T: SystemParam> {
|
||||
param_states: &'s mut T::State,
|
||||
world: UnsafeWorldCell<'w>,
|
||||
|
@ -2124,22 +2084,22 @@ unsafe impl<T: ?Sized> ReadOnlySystemParam for PhantomData<T> {}
|
|||
/// # #[derive(Default, Resource)]
|
||||
/// # struct B;
|
||||
/// #
|
||||
/// let mut world = World::new();
|
||||
/// world.init_resource::<A>();
|
||||
/// world.init_resource::<B>();
|
||||
///
|
||||
/// # let mut world = World::new();
|
||||
/// # world.init_resource::<A>();
|
||||
/// # world.init_resource::<B>();
|
||||
/// #
|
||||
/// // If the inner parameter doesn't require any special building, use `ParamBuilder`.
|
||||
/// // Either specify the type parameter on `DynParamBuilder::new()` ...
|
||||
/// let system = (DynParamBuilder::new::<Res<A>>(ParamBuilder),)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(expects_res_a);
|
||||
/// world.run_system_once(system);
|
||||
/// # world.run_system_once(system);
|
||||
///
|
||||
/// // ... or use a factory method on `ParamBuilder` that returns a specific type.
|
||||
/// let system = (DynParamBuilder::new(ParamBuilder::resource::<A>()),)
|
||||
/// .build_state(&mut world)
|
||||
/// .build_system(expects_res_a);
|
||||
/// world.run_system_once(system);
|
||||
/// # world.run_system_once(system);
|
||||
///
|
||||
/// fn expects_res_a(mut param: DynSystemParam) {
|
||||
/// // Use the `downcast` methods to retrieve the inner parameter.
|
||||
|
@ -2165,7 +2125,7 @@ unsafe impl<T: ?Sized> ReadOnlySystemParam for PhantomData<T> {}
|
|||
/// let local: Local<usize> = param.downcast::<Local<usize>>().unwrap();
|
||||
/// assert_eq!(*local, 10);
|
||||
/// });
|
||||
/// world.run_system_once(system);
|
||||
/// # world.run_system_once(system);
|
||||
/// ```
|
||||
pub struct DynSystemParam<'w, 's> {
|
||||
/// A `ParamState<T>` wrapping the state for the underlying system param.
|
||||
|
|
|
@ -1895,6 +1895,36 @@ impl<'w, 'a, T: Component> VacantEntry<'w, 'a, T> {
|
|||
}
|
||||
|
||||
/// Provides read-only access to a single entity and some of its components defined by the contained [`Access`].
|
||||
///
|
||||
/// To define the access when used as a [`QueryData`](crate::query::QueryData),
|
||||
/// use a [`QueryBuilder`](crate::query::QueryBuilder) or [`QueryParamBuilder`](crate::system::QueryParamBuilder).
|
||||
/// The `FilteredEntityRef` must be the entire `QueryData`, and not nested inside a tuple with other data.
|
||||
///
|
||||
/// ```
|
||||
/// # use bevy_ecs::{prelude::*, world::FilteredEntityRef};
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct A;
|
||||
/// #
|
||||
/// # let mut world = World::new();
|
||||
/// # world.spawn(A);
|
||||
/// #
|
||||
/// // This gives the `FilteredEntityRef` access to `&A`.
|
||||
/// let mut query = QueryBuilder::<FilteredEntityRef>::new(&mut world)
|
||||
/// .data::<&A>()
|
||||
/// .build();
|
||||
///
|
||||
/// let filtered_entity: FilteredEntityRef = query.single(&mut world);
|
||||
/// let component: &A = filtered_entity.get().unwrap();
|
||||
///
|
||||
/// // Here `FilteredEntityRef` is nested in a tuple, so it does not have access to `&A`.
|
||||
/// let mut query = QueryBuilder::<(Entity, FilteredEntityRef)>::new(&mut world)
|
||||
/// .data::<&A>()
|
||||
/// .build();
|
||||
///
|
||||
/// let (_, filtered_entity) = query.single(&mut world);
|
||||
/// assert!(filtered_entity.get::<A>().is_none());
|
||||
/// ```
|
||||
#[derive(Clone)]
|
||||
pub struct FilteredEntityRef<'w> {
|
||||
entity: UnsafeEntityCell<'w>,
|
||||
|
@ -2136,6 +2166,36 @@ impl<'a> From<&'a EntityWorldMut<'_>> for FilteredEntityRef<'a> {
|
|||
}
|
||||
|
||||
/// Provides mutable access to a single entity and some of its components defined by the contained [`Access`].
|
||||
///
|
||||
/// To define the access when used as a [`QueryData`](crate::query::QueryData),
|
||||
/// use a [`QueryBuilder`](crate::query::QueryBuilder) or [`QueryParamBuilder`](crate::system::QueryParamBuilder).
|
||||
/// The `FilteredEntityMut` must be the entire `QueryData`, and not nested inside a tuple with other data.
|
||||
///
|
||||
/// ```
|
||||
/// # use bevy_ecs::{prelude::*, world::FilteredEntityMut};
|
||||
/// #
|
||||
/// # #[derive(Component)]
|
||||
/// # struct A;
|
||||
/// #
|
||||
/// # let mut world = World::new();
|
||||
/// # world.spawn(A);
|
||||
/// #
|
||||
/// // This gives the `FilteredEntityMut` access to `&mut A`.
|
||||
/// let mut query = QueryBuilder::<FilteredEntityMut>::new(&mut world)
|
||||
/// .data::<&mut A>()
|
||||
/// .build();
|
||||
///
|
||||
/// let mut filtered_entity: FilteredEntityMut = query.single_mut(&mut world);
|
||||
/// let component: Mut<A> = filtered_entity.get_mut().unwrap();
|
||||
///
|
||||
/// // Here `FilteredEntityMut` is nested in a tuple, so it does not have access to `&mut A`.
|
||||
/// let mut query = QueryBuilder::<(Entity, FilteredEntityMut)>::new(&mut world)
|
||||
/// .data::<&mut A>()
|
||||
/// .build();
|
||||
///
|
||||
/// let (_, mut filtered_entity) = query.single_mut(&mut world);
|
||||
/// assert!(filtered_entity.get_mut::<A>().is_none());
|
||||
/// ```
|
||||
pub struct FilteredEntityMut<'w> {
|
||||
entity: UnsafeEntityCell<'w>,
|
||||
access: Access<ComponentId>,
|
||||
|
|
Loading…
Reference in a new issue