From ee75aa1e0dbc504665a0f24d2144c9354a6df5bf Mon Sep 17 00:00:00 2001 From: Doug Roeper Date: Thu, 25 Jan 2024 08:01:11 -0500 Subject: [PATCH] Fix bug where events where not being dropped --- crates/bevy_app/src/app.rs | 4 +++- crates/bevy_ecs/src/event.rs | 45 ++++++++++++++++++++++++++++-------- crates/bevy_time/src/lib.rs | 5 ++-- 3 files changed, 41 insertions(+), 13 deletions(-) diff --git a/crates/bevy_app/src/app.rs b/crates/bevy_app/src/app.rs index f117db2e77e405..26e16eba22a392 100644 --- a/crates/bevy_app/src/app.rs +++ b/crates/bevy_app/src/app.rs @@ -1,4 +1,4 @@ -use crate::{First, Main, MainSchedulePlugin, Plugin, Plugins, StateTransition}; +use crate::{First, FixedPostUpdate, Main, MainSchedulePlugin, Plugin, Plugins, StateTransition}; pub use bevy_derive::AppLabel; use bevy_ecs::{ prelude::*, @@ -507,6 +507,8 @@ impl App { bevy_ecs::event::event_update_system:: .run_if(bevy_ecs::event::event_update_condition::), ); + self.init_resource::>() + .add_systems(FixedPostUpdate, bevy_ecs::event::event_queue_update_system::); } self } diff --git a/crates/bevy_ecs/src/event.rs b/crates/bevy_ecs/src/event.rs index 8b25ab2a2cbc84..bf971b5bd5aeef 100644 --- a/crates/bevy_ecs/src/event.rs +++ b/crates/bevy_ecs/src/event.rs @@ -13,6 +13,8 @@ use std::{ marker::PhantomData, slice::Iter, }; +use bevy_utils::tracing::error; + /// A type that can be stored in an [`Events`] resource /// You can conveniently access events using the [`EventReader`] and [`EventWriter`] system parameter. /// @@ -33,6 +35,7 @@ pub struct EventId { } impl Copy for EventId {} + impl Clone for EventId { fn clone(&self) -> Self { *self @@ -747,27 +750,51 @@ impl<'a, E: Event> ExactSizeIterator for EventIteratorWithId<'a, E> { } } +#[doc(hidden)] +#[derive(Resource)] +pub struct EventUpdateSignal { + signal: bool, + _marker: PhantomData T>, +} + +impl Default for EventUpdateSignal { + fn default() -> Self { + Self { + signal: false, + _marker: PhantomData, + } + } +} + #[doc(hidden)] #[derive(Resource, Default)] -pub struct EventUpdateSignal(bool); +pub struct EventUpdateShouldWaitForFixedUpdate; /// A system that queues a call to [`Events::update`]. -pub fn event_queue_update_system(signal: Option>) { +pub fn event_queue_update_system(signal: Option>>) { if let Some(mut s) = signal { - s.0 = true; + s.signal = true; } } /// A system that calls [`Events::update`]. pub fn event_update_system( - signal: Option>, + should_wait: Option>, + mut should_update: Option>>, mut events: ResMut>, ) { - if let Some(mut s) = signal { - // If we haven't got a signal to update the events, but we *could* get such a signal - // return early and update the events later. - if !std::mem::replace(&mut s.0, false) { - return; + if should_wait.is_some() { + match should_update { + Some(mut should_update) => { + // If we haven't got a signal to update the events, but we *could* get such a signal + // return early and update the events later. + if !std::mem::replace(&mut should_update.signal, false) { + return; + } + } + None => { + error!("EventUpdateSignal<{0}> resource not found but fixed update systems are active. Please add EventUpdateSignal<{0}> as a resource", std::any::type_name::()); + } } } diff --git a/crates/bevy_time/src/lib.rs b/crates/bevy_time/src/lib.rs index 9b7e7a1ea21cc5..04a11fbcbc9bf3 100644 --- a/crates/bevy_time/src/lib.rs +++ b/crates/bevy_time/src/lib.rs @@ -25,7 +25,7 @@ pub mod prelude { } use bevy_app::{prelude::*, RunFixedMainLoop}; -use bevy_ecs::event::{event_queue_update_system, EventUpdateSignal}; +use bevy_ecs::event::{EventUpdateShouldWaitForFixedUpdate}; use bevy_ecs::prelude::*; use bevy_utils::{tracing::warn, Duration, Instant}; pub use crossbeam_channel::TrySendError; @@ -60,8 +60,7 @@ impl Plugin for TimePlugin { .add_systems(RunFixedMainLoop, run_fixed_main_schedule); // ensure the events are not dropped until `FixedMain` systems can observe them - app.init_resource::() - .add_systems(FixedPostUpdate, event_queue_update_system); + app.init_resource::(); #[cfg(feature = "bevy_ci_testing")] if let Some(ci_testing_config) = app