Add send_event
and friends to WorldCell
(#6515)
# Objective Copy `send_event` and friends from `World` to `WorldCell`. Clean up `bevy_winit` using `WorldCell::send_event`. ## Changelog Added `send_event`, `send_event_default`, and `send_event_batch` to `WorldCell`. Co-authored-by: devil-ira <justthecooldude@gmail.com>
This commit is contained in:
parent
4ad621fe0f
commit
d688ba5f29
@ -1,5 +1,8 @@
|
||||
use bevy_utils::tracing::error;
|
||||
|
||||
use crate::{
|
||||
archetype::ArchetypeComponentId,
|
||||
event::{Event, Events},
|
||||
storage::SparseSet,
|
||||
system::Resource,
|
||||
world::{Mut, World},
|
||||
@ -317,6 +320,30 @@ impl<'w> WorldCell<'w> {
|
||||
),
|
||||
}
|
||||
}
|
||||
|
||||
/// Sends an [`Event`](crate::event::Event).
|
||||
#[inline]
|
||||
pub fn send_event<E: Event>(&self, event: E) {
|
||||
self.send_event_batch(std::iter::once(event));
|
||||
}
|
||||
|
||||
/// Sends the default value of the [`Event`](crate::event::Event) of type `E`.
|
||||
#[inline]
|
||||
pub fn send_event_default<E: Event + Default>(&self) {
|
||||
self.send_event_batch(std::iter::once(E::default()));
|
||||
}
|
||||
|
||||
/// Sends a batch of [`Event`](crate::event::Event)s from an iterator.
|
||||
#[inline]
|
||||
pub fn send_event_batch<E: Event>(&self, events: impl Iterator<Item = E>) {
|
||||
match self.get_resource_mut::<Events<E>>() {
|
||||
Some(mut events_resource) => events_resource.extend(events),
|
||||
None => error!(
|
||||
"Unable to send event `{}`\n\tEvent must be added to the app with `add_event()`\n\thttps://docs.rs/bevy/*/bevy/app/struct.App.html#method.add_event ",
|
||||
std::any::type_name::<E>()
|
||||
),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
@ -23,10 +23,7 @@ pub mod prelude {
|
||||
}
|
||||
|
||||
use bevy_app::prelude::*;
|
||||
use bevy_ecs::{
|
||||
event::Events,
|
||||
schedule::{IntoSystemDescriptor, SystemLabel},
|
||||
};
|
||||
use bevy_ecs::schedule::{IntoSystemDescriptor, SystemLabel};
|
||||
|
||||
impl Default for WindowPlugin {
|
||||
fn default() -> Self {
|
||||
@ -85,8 +82,7 @@ impl Plugin for WindowPlugin {
|
||||
.init_resource::<Windows>();
|
||||
|
||||
if self.add_primary_window {
|
||||
let mut create_window_event = app.world.resource_mut::<Events<CreateWindow>>();
|
||||
create_window_event.send(CreateWindow {
|
||||
app.world.send_event(CreateWindow {
|
||||
id: WindowId::primary(),
|
||||
descriptor: self.window.clone(),
|
||||
});
|
||||
|
@ -14,11 +14,7 @@ use bevy_ecs::{
|
||||
event::{Events, ManualEventReader},
|
||||
world::World,
|
||||
};
|
||||
use bevy_input::{
|
||||
keyboard::KeyboardInput,
|
||||
mouse::{MouseButtonInput, MouseMotion, MouseScrollUnit, MouseWheel},
|
||||
touch::TouchInput,
|
||||
};
|
||||
use bevy_input::mouse::{MouseButtonInput, MouseMotion, MouseScrollUnit, MouseWheel};
|
||||
use bevy_math::{ivec2, DVec2, UVec2, Vec2};
|
||||
use bevy_utils::{
|
||||
tracing::{error, info, trace, warn},
|
||||
@ -408,67 +404,51 @@ pub fn winit_runner_with(mut app: App) {
|
||||
match event {
|
||||
WindowEvent::Resized(size) => {
|
||||
window.update_actual_size_from_backend(size.width, size.height);
|
||||
let mut resize_events = world.resource_mut::<Events<WindowResized>>();
|
||||
resize_events.send(WindowResized {
|
||||
world.send_event(WindowResized {
|
||||
id: window_id,
|
||||
width: window.width(),
|
||||
height: window.height(),
|
||||
});
|
||||
}
|
||||
WindowEvent::CloseRequested => {
|
||||
let mut window_close_requested_events =
|
||||
world.resource_mut::<Events<WindowCloseRequested>>();
|
||||
window_close_requested_events.send(WindowCloseRequested { id: window_id });
|
||||
world.send_event(WindowCloseRequested { id: window_id });
|
||||
}
|
||||
WindowEvent::KeyboardInput { ref input, .. } => {
|
||||
let mut keyboard_input_events =
|
||||
world.resource_mut::<Events<KeyboardInput>>();
|
||||
keyboard_input_events.send(converters::convert_keyboard_input(input));
|
||||
world.send_event(converters::convert_keyboard_input(input));
|
||||
}
|
||||
WindowEvent::CursorMoved { position, .. } => {
|
||||
let mut cursor_moved_events = world.resource_mut::<Events<CursorMoved>>();
|
||||
|
||||
let physical_position = DVec2::new(position.x, position.y);
|
||||
window
|
||||
.update_cursor_physical_position_from_backend(Some(physical_position));
|
||||
|
||||
cursor_moved_events.send(CursorMoved {
|
||||
world.send_event(CursorMoved {
|
||||
id: window_id,
|
||||
position: (physical_position / window.scale_factor()).as_vec2(),
|
||||
});
|
||||
}
|
||||
WindowEvent::CursorEntered { .. } => {
|
||||
let mut cursor_entered_events =
|
||||
world.resource_mut::<Events<CursorEntered>>();
|
||||
cursor_entered_events.send(CursorEntered { id: window_id });
|
||||
world.send_event(CursorEntered { id: window_id });
|
||||
}
|
||||
WindowEvent::CursorLeft { .. } => {
|
||||
let mut cursor_left_events = world.resource_mut::<Events<CursorLeft>>();
|
||||
window.update_cursor_physical_position_from_backend(None);
|
||||
cursor_left_events.send(CursorLeft { id: window_id });
|
||||
world.send_event(CursorLeft { id: window_id });
|
||||
}
|
||||
WindowEvent::MouseInput { state, button, .. } => {
|
||||
let mut mouse_button_input_events =
|
||||
world.resource_mut::<Events<MouseButtonInput>>();
|
||||
mouse_button_input_events.send(MouseButtonInput {
|
||||
world.send_event(MouseButtonInput {
|
||||
button: converters::convert_mouse_button(button),
|
||||
state: converters::convert_element_state(state),
|
||||
});
|
||||
}
|
||||
WindowEvent::MouseWheel { delta, .. } => match delta {
|
||||
event::MouseScrollDelta::LineDelta(x, y) => {
|
||||
let mut mouse_wheel_input_events =
|
||||
world.resource_mut::<Events<MouseWheel>>();
|
||||
mouse_wheel_input_events.send(MouseWheel {
|
||||
world.send_event(MouseWheel {
|
||||
unit: MouseScrollUnit::Line,
|
||||
x,
|
||||
y,
|
||||
});
|
||||
}
|
||||
event::MouseScrollDelta::PixelDelta(p) => {
|
||||
let mut mouse_wheel_input_events =
|
||||
world.resource_mut::<Events<MouseWheel>>();
|
||||
mouse_wheel_input_events.send(MouseWheel {
|
||||
world.send_event(MouseWheel {
|
||||
unit: MouseScrollUnit::Pixel,
|
||||
x: p.x as f32,
|
||||
y: p.y as f32,
|
||||
@ -476,8 +456,6 @@ pub fn winit_runner_with(mut app: App) {
|
||||
}
|
||||
},
|
||||
WindowEvent::Touch(touch) => {
|
||||
let mut touch_input_events = world.resource_mut::<Events<TouchInput>>();
|
||||
|
||||
let mut location = touch.location.to_logical(window.scale_factor());
|
||||
|
||||
// On a mobile window, the start is from the top while on PC/Linux/OSX from
|
||||
@ -486,13 +464,11 @@ pub fn winit_runner_with(mut app: App) {
|
||||
let window_height = windows.primary().height();
|
||||
location.y = window_height - location.y;
|
||||
}
|
||||
touch_input_events.send(converters::convert_touch_input(touch, location));
|
||||
|
||||
world.send_event(converters::convert_touch_input(touch, location));
|
||||
}
|
||||
WindowEvent::ReceivedCharacter(c) => {
|
||||
let mut char_input_events =
|
||||
world.resource_mut::<Events<ReceivedCharacter>>();
|
||||
|
||||
char_input_events.send(ReceivedCharacter {
|
||||
world.send_event(ReceivedCharacter {
|
||||
id: window_id,
|
||||
char: c,
|
||||
});
|
||||
@ -501,9 +477,7 @@ pub fn winit_runner_with(mut app: App) {
|
||||
scale_factor,
|
||||
new_inner_size,
|
||||
} => {
|
||||
let mut backend_scale_factor_change_events =
|
||||
world.resource_mut::<Events<WindowBackendScaleFactorChanged>>();
|
||||
backend_scale_factor_change_events.send(WindowBackendScaleFactorChanged {
|
||||
world.send_event(WindowBackendScaleFactorChanged {
|
||||
id: window_id,
|
||||
scale_factor,
|
||||
});
|
||||
@ -521,10 +495,7 @@ pub fn winit_runner_with(mut app: App) {
|
||||
)
|
||||
.to_physical::<u32>(forced_factor);
|
||||
} else if approx::relative_ne!(new_factor, prior_factor) {
|
||||
let mut scale_factor_change_events =
|
||||
world.resource_mut::<Events<WindowScaleFactorChanged>>();
|
||||
|
||||
scale_factor_change_events.send(WindowScaleFactorChanged {
|
||||
world.send_event(WindowScaleFactorChanged {
|
||||
id: window_id,
|
||||
scale_factor,
|
||||
});
|
||||
@ -535,8 +506,7 @@ pub fn winit_runner_with(mut app: App) {
|
||||
if approx::relative_ne!(window.width() as f64, new_logical_width)
|
||||
|| approx::relative_ne!(window.height() as f64, new_logical_height)
|
||||
{
|
||||
let mut resize_events = world.resource_mut::<Events<WindowResized>>();
|
||||
resize_events.send(WindowResized {
|
||||
world.send_event(WindowResized {
|
||||
id: window_id,
|
||||
width: new_logical_width as f32,
|
||||
height: new_logical_height as f32,
|
||||
@ -549,35 +519,30 @@ pub fn winit_runner_with(mut app: App) {
|
||||
}
|
||||
WindowEvent::Focused(focused) => {
|
||||
window.update_focused_status_from_backend(focused);
|
||||
let mut focused_events = world.resource_mut::<Events<WindowFocused>>();
|
||||
focused_events.send(WindowFocused {
|
||||
world.send_event(WindowFocused {
|
||||
id: window_id,
|
||||
focused,
|
||||
});
|
||||
}
|
||||
WindowEvent::DroppedFile(path_buf) => {
|
||||
let mut events = world.resource_mut::<Events<FileDragAndDrop>>();
|
||||
events.send(FileDragAndDrop::DroppedFile {
|
||||
world.send_event(FileDragAndDrop::DroppedFile {
|
||||
id: window_id,
|
||||
path_buf,
|
||||
});
|
||||
}
|
||||
WindowEvent::HoveredFile(path_buf) => {
|
||||
let mut events = world.resource_mut::<Events<FileDragAndDrop>>();
|
||||
events.send(FileDragAndDrop::HoveredFile {
|
||||
world.send_event(FileDragAndDrop::HoveredFile {
|
||||
id: window_id,
|
||||
path_buf,
|
||||
});
|
||||
}
|
||||
WindowEvent::HoveredFileCancelled => {
|
||||
let mut events = world.resource_mut::<Events<FileDragAndDrop>>();
|
||||
events.send(FileDragAndDrop::HoveredFileCancelled { id: window_id });
|
||||
world.send_event(FileDragAndDrop::HoveredFileCancelled { id: window_id });
|
||||
}
|
||||
WindowEvent::Moved(position) => {
|
||||
let position = ivec2(position.x, position.y);
|
||||
window.update_actual_position_from_backend(position);
|
||||
let mut events = world.resource_mut::<Events<WindowMoved>>();
|
||||
events.send(WindowMoved {
|
||||
world.send_event(WindowMoved {
|
||||
id: window_id,
|
||||
position,
|
||||
});
|
||||
@ -589,8 +554,7 @@ pub fn winit_runner_with(mut app: App) {
|
||||
event: DeviceEvent::MouseMotion { delta: (x, y) },
|
||||
..
|
||||
} => {
|
||||
let mut mouse_motion_events = app.world.resource_mut::<Events<MouseMotion>>();
|
||||
mouse_motion_events.send(MouseMotion {
|
||||
app.world.send_event(MouseMotion {
|
||||
delta: DVec2 { x, y }.as_vec2(),
|
||||
});
|
||||
}
|
||||
@ -681,9 +645,6 @@ fn handle_create_window_events(
|
||||
let mut winit_windows = world.non_send_resource_mut::<WinitWindows>();
|
||||
let mut windows = world.resource_mut::<Windows>();
|
||||
let create_window_events = world.resource::<Events<CreateWindow>>();
|
||||
let mut window_created_events = world.resource_mut::<Events<WindowCreated>>();
|
||||
#[cfg(not(any(target_os = "windows", target_feature = "x11")))]
|
||||
let mut window_resized_events = world.resource_mut::<Events<WindowResized>>();
|
||||
for create_window_event in create_window_event_reader.iter(&create_window_events) {
|
||||
let window = winit_windows.create_window(
|
||||
event_loop,
|
||||
@ -694,13 +655,13 @@ fn handle_create_window_events(
|
||||
// TODO: we aren't yet sure about native wayland, so we might be able to exclude it,
|
||||
// but sending a duplicate event isn't problematic, as windows already does this.
|
||||
#[cfg(not(any(target_os = "windows", target_feature = "x11")))]
|
||||
window_resized_events.send(WindowResized {
|
||||
world.send_event(WindowResized {
|
||||
id: create_window_event.id,
|
||||
width: window.width(),
|
||||
height: window.height(),
|
||||
});
|
||||
windows.add(window);
|
||||
window_created_events.send(WindowCreated {
|
||||
world.send_event(WindowCreated {
|
||||
id: create_window_event.id,
|
||||
});
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user