Merge branch 'main' into val-physical-resolve

This commit is contained in:
ickshonpe 2025-05-26 17:03:34 +01:00 committed by GitHub
commit 0516a9bee6
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
11 changed files with 39 additions and 123 deletions

View File

@ -10,7 +10,7 @@ keywords = ["game", "engine", "gamedev", "graphics", "bevy"]
license = "MIT OR Apache-2.0"
repository = "https://github.com/bevyengine/bevy"
documentation = "https://docs.rs/bevy"
rust-version = "1.85.0"
rust-version = "1.86.0"
[workspace]
resolver = "2"

View File

@ -205,8 +205,6 @@ pub fn derive_enum_variant_meta(input: TokenStream) -> TokenStream {
pub fn derive_app_label(input: TokenStream) -> TokenStream {
let input = syn::parse_macro_input!(input as syn::DeriveInput);
let mut trait_path = BevyManifest::shared().get_path("bevy_app");
let mut dyn_eq_path = trait_path.clone();
trait_path.segments.push(format_ident!("AppLabel").into());
dyn_eq_path.segments.push(format_ident!("DynEq").into());
derive_label(input, "AppLabel", &trait_path, &dyn_eq_path)
derive_label(input, "AppLabel", &trait_path)
}

View File

@ -1,7 +1,6 @@
//! Text and on-screen debugging tools
use bevy_app::prelude::*;
use bevy_asset::prelude::*;
use bevy_color::prelude::*;
use bevy_ecs::prelude::*;
use bevy_picking::backend::HitData;
@ -248,25 +247,18 @@ pub fn debug_draw(
pointers: Query<(Entity, &PointerId, &PointerDebug)>,
scale: Res<UiScale>,
) {
let font_handle: Handle<Font> = Default::default();
for (entity, id, debug) in pointers.iter() {
for (entity, id, debug) in &pointers {
let Some(pointer_location) = &debug.location else {
continue;
};
let text = format!("{id:?}\n{debug}");
for camera in camera_query
.iter()
.map(|(entity, camera)| {
(
entity,
camera.target.normalize(primary_window.single().ok()),
)
})
.filter_map(|(entity, target)| Some(entity).zip(target))
.filter(|(_entity, target)| target == &pointer_location.target)
.map(|(cam_entity, _target)| cam_entity)
{
for (camera, _) in camera_query.iter().filter(|(_, camera)| {
camera
.target
.normalize(primary_window.single().ok())
.is_some_and(|target| target == pointer_location.target)
}) {
let mut pointer_pos = pointer_location.position;
if let Some(viewport) = camera_query
.get(camera)
@ -278,23 +270,21 @@ pub fn debug_draw(
commands
.entity(entity)
.despawn_related::<Children>()
.insert((
Text::new(text.clone()),
TextFont {
font: font_handle.clone(),
font_size: 12.0,
..Default::default()
},
TextColor(Color::WHITE),
Node {
position_type: PositionType::Absolute,
left: Val::Px(pointer_pos.x + 5.0) / scale.0,
top: Val::Px(pointer_pos.y + 5.0) / scale.0,
padding: UiRect::px(10.0, 10.0, 8.0, 6.0),
..Default::default()
},
))
.insert(Pickable::IGNORE)
.insert(UiTargetCamera(camera));
BackgroundColor(Color::BLACK.with_alpha(0.75)),
GlobalZIndex(i32::MAX),
Pickable::IGNORE,
UiTargetCamera(camera),
children![(Text::new(text.clone()), TextFont::from_font_size(12.0))],
));
}
}
}

View File

@ -8,7 +8,7 @@ repository = "https://github.com/bevyengine/bevy"
license = "MIT OR Apache-2.0"
keywords = ["ecs", "game", "bevy"]
categories = ["game-engines", "data-structures"]
rust-version = "1.85.0"
rust-version = "1.86.0"
[features]
default = ["std", "bevy_reflect", "async_executor", "backtrace"]

View File

@ -503,12 +503,10 @@ pub fn derive_schedule_label(input: TokenStream) -> TokenStream {
let input = parse_macro_input!(input as DeriveInput);
let mut trait_path = bevy_ecs_path();
trait_path.segments.push(format_ident!("schedule").into());
let mut dyn_eq_path = trait_path.clone();
trait_path
.segments
.push(format_ident!("ScheduleLabel").into());
dyn_eq_path.segments.push(format_ident!("DynEq").into());
derive_label(input, "ScheduleLabel", &trait_path, &dyn_eq_path)
derive_label(input, "ScheduleLabel", &trait_path)
}
/// Derive macro generating an impl of the trait `SystemSet`.
@ -519,10 +517,8 @@ pub fn derive_system_set(input: TokenStream) -> TokenStream {
let input = parse_macro_input!(input as DeriveInput);
let mut trait_path = bevy_ecs_path();
trait_path.segments.push(format_ident!("schedule").into());
let mut dyn_eq_path = trait_path.clone();
trait_path.segments.push(format_ident!("SystemSet").into());
dyn_eq_path.segments.push(format_ident!("DynEq").into());
derive_label(input, "SystemSet", &trait_path, &dyn_eq_path)
derive_label(input, "SystemSet", &trait_path)
}
pub(crate) fn bevy_ecs_path() -> syn::Path {

View File

@ -12,9 +12,6 @@ pub use alloc::boxed::Box;
/// An object safe version of [`Eq`]. This trait is automatically implemented
/// for any `'static` type that implements `Eq`.
pub trait DynEq: Any {
/// Casts the type to `dyn Any`.
fn as_any(&self) -> &dyn Any;
/// This method tests for `self` and `other` values to be equal.
///
/// Implementers should avoid returning `true` when the underlying types are
@ -29,12 +26,8 @@ impl<T> DynEq for T
where
T: Any + Eq,
{
fn as_any(&self) -> &dyn Any {
self
}
fn dyn_eq(&self, other: &dyn DynEq) -> bool {
if let Some(other) = other.as_any().downcast_ref::<T>() {
if let Some(other) = (other as &dyn Any).downcast_ref::<T>() {
return self == other;
}
false
@ -44,9 +37,6 @@ where
/// An object safe version of [`Hash`]. This trait is automatically implemented
/// for any `'static` type that implements `Hash`.
pub trait DynHash: DynEq {
/// Casts the type to `dyn Any`.
fn as_dyn_eq(&self) -> &dyn DynEq;
/// Feeds this value into the given [`Hasher`].
fn dyn_hash(&self, state: &mut dyn Hasher);
}
@ -58,10 +48,6 @@ impl<T> DynHash for T
where
T: DynEq + Hash,
{
fn as_dyn_eq(&self) -> &dyn DynEq {
self
}
fn dyn_hash(&self, mut state: &mut dyn Hasher) {
T::hash(self, &mut state);
self.type_id().hash(&mut state);
@ -120,7 +106,7 @@ macro_rules! define_label {
) => {
$(#[$label_attr])*
pub trait $label_trait_name: 'static + Send + Sync + ::core::fmt::Debug {
pub trait $label_trait_name: Send + Sync + ::core::fmt::Debug + $crate::label::DynEq + $crate::label::DynHash {
$($trait_extra_methods)*
@ -129,12 +115,6 @@ macro_rules! define_label {
///`.
fn dyn_clone(&self) -> $crate::label::Box<dyn $label_trait_name>;
/// Casts this value to a form where it can be compared with other type-erased values.
fn as_dyn_eq(&self) -> &dyn $crate::label::DynEq;
/// Feeds this value into the given [`Hasher`].
fn dyn_hash(&self, state: &mut dyn ::core::hash::Hasher);
/// Returns an [`Interned`] value corresponding to `self`.
fn intern(&self) -> $crate::intern::Interned<dyn $label_trait_name>
where Self: Sized {
@ -151,15 +131,6 @@ macro_rules! define_label {
(**self).dyn_clone()
}
/// Casts this value to a form where it can be compared with other type-erased values.
fn as_dyn_eq(&self) -> &dyn $crate::label::DynEq {
(**self).as_dyn_eq()
}
fn dyn_hash(&self, state: &mut dyn ::core::hash::Hasher) {
(**self).dyn_hash(state);
}
fn intern(&self) -> Self {
*self
}
@ -167,7 +138,7 @@ macro_rules! define_label {
impl PartialEq for dyn $label_trait_name {
fn eq(&self, other: &Self) -> bool {
self.as_dyn_eq().dyn_eq(other.as_dyn_eq())
self.dyn_eq(other)
}
}
@ -188,7 +159,7 @@ macro_rules! define_label {
use ::core::ptr;
// Test that both the type id and pointer address are equivalent.
self.as_dyn_eq().type_id() == other.as_dyn_eq().type_id()
self.type_id() == other.type_id()
&& ptr::addr_eq(ptr::from_ref::<Self>(self), ptr::from_ref::<Self>(other))
}
@ -196,7 +167,7 @@ macro_rules! define_label {
use ::core::{hash::Hash, ptr};
// Hash the type id...
self.as_dyn_eq().type_id().hash(state);
self.type_id().hash(state);
// ...and the pointer address.
// Cast to a unit `()` first to discard any pointer metadata.

View File

@ -147,15 +147,6 @@ impl<T> SystemSet for SystemTypeSet<T> {
fn dyn_clone(&self) -> Box<dyn SystemSet> {
Box::new(*self)
}
fn as_dyn_eq(&self) -> &dyn DynEq {
self
}
fn dyn_hash(&self, mut state: &mut dyn Hasher) {
TypeId::of::<Self>().hash(&mut state);
self.hash(&mut state);
}
}
/// A [`SystemSet`] implicitly created when using
@ -178,15 +169,6 @@ impl SystemSet for AnonymousSet {
fn dyn_clone(&self) -> Box<dyn SystemSet> {
Box::new(*self)
}
fn as_dyn_eq(&self) -> &dyn DynEq {
self
}
fn dyn_hash(&self, mut state: &mut dyn Hasher) {
TypeId::of::<Self>().hash(&mut state);
self.hash(&mut state);
}
}
/// Types that can be converted into a [`SystemSet`].

View File

@ -1675,7 +1675,7 @@ unsafe impl<'a> SystemParam for &'a Bundles {
/// Component change ticks that are more recent than `last_run` will be detected by the system.
/// Those can be read by calling [`last_changed`](crate::change_detection::DetectChanges::last_changed)
/// on a [`Mut<T>`](crate::change_detection::Mut) or [`ResMut<T>`](ResMut).
#[derive(Debug)]
#[derive(Debug, Clone, Copy)]
pub struct SystemChangeTick {
last_run: Tick,
this_run: Tick,
@ -2510,10 +2510,7 @@ impl DynSystemParamState {
}
/// Allows a [`SystemParam::State`] to be used as a trait object for implementing [`DynSystemParam`].
trait DynParamState: Sync + Send {
/// Casts the underlying `ParamState<T>` to an `Any` so it can be downcast.
fn as_any_mut(&mut self) -> &mut dyn Any;
trait DynParamState: Sync + Send + Any {
/// For the specified [`Archetype`], registers the components accessed by this [`SystemParam`] (if applicable).a
///
/// # Safety
@ -2544,10 +2541,6 @@ trait DynParamState: Sync + Send {
struct ParamState<T: SystemParam>(T::State);
impl<T: SystemParam + 'static> DynParamState for ParamState<T> {
fn as_any_mut(&mut self) -> &mut dyn Any {
self
}
unsafe fn new_archetype(&mut self, archetype: &Archetype, system_meta: &mut SystemMeta) {
// SAFETY: The caller ensures that `archetype` is from the World the state was initialized from in `init_state`.
unsafe { T::new_archetype(&mut self.0, archetype, system_meta) };
@ -2597,18 +2590,11 @@ unsafe impl SystemParam for DynSystemParam<'_, '_> {
change_tick: Tick,
) -> Self::Item<'world, 'state> {
// SAFETY:
// - `state.0` is a boxed `ParamState<T>`, and its implementation of `as_any_mut` returns `self`.
// - `state.0` is a boxed `ParamState<T>`.
// - The state was obtained from `SystemParamBuilder::build()`, which registers all [`World`] accesses used
// by [`SystemParam::get_param`] with the provided [`system_meta`](SystemMeta).
// - The caller ensures that the provided world is the same and has the required access.
unsafe {
DynSystemParam::new(
state.0.as_any_mut(),
world,
system_meta.clone(),
change_tick,
)
}
unsafe { DynSystemParam::new(state.0.as_mut(), world, system_meta.clone(), change_tick) }
}
unsafe fn new_archetype(

View File

@ -58,7 +58,6 @@ pub fn derive_label(
input: syn::DeriveInput,
trait_name: &str,
trait_path: &syn::Path,
dyn_eq_path: &syn::Path,
) -> TokenStream {
if let syn::Data::Union(_) = &input.data {
let message = format!("Cannot derive {trait_name} for unions.");
@ -89,16 +88,6 @@ pub fn derive_label(
fn dyn_clone(&self) -> alloc::boxed::Box<dyn #trait_path> {
alloc::boxed::Box::new(::core::clone::Clone::clone(self))
}
fn as_dyn_eq(&self) -> &dyn #dyn_eq_path {
self
}
fn dyn_hash(&self, mut state: &mut dyn ::core::hash::Hasher) {
let ty_id = ::core::any::TypeId::of::<Self>();
::core::hash::Hash::hash(&ty_id, &mut state);
::core::hash::Hash::hash(self, &mut state);
}
}
};
}

View File

@ -80,12 +80,10 @@ pub fn derive_render_label(input: TokenStream) -> TokenStream {
trait_path
.segments
.push(format_ident!("render_graph").into());
let mut dyn_eq_path = trait_path.clone();
trait_path
.segments
.push(format_ident!("RenderLabel").into());
dyn_eq_path.segments.push(format_ident!("DynEq").into());
derive_label(input, "RenderLabel", &trait_path, &dyn_eq_path)
derive_label(input, "RenderLabel", &trait_path)
}
/// Derive macro generating an impl of the trait `RenderSubGraph`.
@ -98,10 +96,8 @@ pub fn derive_render_sub_graph(input: TokenStream) -> TokenStream {
trait_path
.segments
.push(format_ident!("render_graph").into());
let mut dyn_eq_path = trait_path.clone();
trait_path
.segments
.push(format_ident!("RenderSubGraph").into());
dyn_eq_path.segments.push(format_ident!("DynEq").into());
derive_label(input, "RenderSubGraph", &trait_path, &dyn_eq_path)
derive_label(input, "RenderSubGraph", &trait_path)
}

View File

@ -0,0 +1,8 @@
---
title: Interned labels cleanup
pull_requests: [18984]
---
- `DynEq::as_any` has been removed. Use `&value as &dyn Any` instead.
- `DynHash::as_dyn_eq` has been removed. Use `&value as &dyn DynEq` instead.
- `as_dyn_eq` has been removed from 'label' types such as `ScheduleLabel` and `SystemSet`. Call `DynEq::dyn_eq` directly on the label instead.