gamepad: expose raw and filtered gamepad events. (#711)
This commit is contained in:
parent
894cc5e40a
commit
267599e577
@ -231,8 +231,8 @@ name = "gamepad_input"
|
||||
path = "examples/input/gamepad_input.rs"
|
||||
|
||||
[[example]]
|
||||
name = "gamepad_input_event"
|
||||
path = "examples/input/gamepad_input_event.rs"
|
||||
name = "gamepad_input_events"
|
||||
path = "examples/input/gamepad_input_events.rs"
|
||||
|
||||
[[example]]
|
||||
name = "touch_input"
|
||||
|
@ -174,7 +174,8 @@ impl AppBuilder {
|
||||
.add_startup_stage(startup_stage::STARTUP)
|
||||
.add_startup_stage(startup_stage::POST_STARTUP)
|
||||
.add_stage(stage::FIRST)
|
||||
.add_stage(stage::EVENT_UPDATE)
|
||||
.add_stage(stage::PRE_EVENT)
|
||||
.add_stage(stage::EVENT)
|
||||
.add_stage(stage::PRE_UPDATE)
|
||||
.add_stage(stage::UPDATE)
|
||||
.add_stage(stage::POST_UPDATE)
|
||||
@ -217,7 +218,7 @@ impl AppBuilder {
|
||||
T: Send + Sync + 'static,
|
||||
{
|
||||
self.add_resource(Events::<T>::default())
|
||||
.add_system_to_stage(stage::EVENT_UPDATE, Events::<T>::update_system.system())
|
||||
.add_system_to_stage(stage::EVENT, Events::<T>::update_system.system())
|
||||
}
|
||||
|
||||
pub fn add_resource<T>(&mut self, resource: T) -> &mut Self
|
||||
|
@ -1,8 +1,11 @@
|
||||
/// Name of app stage that runs before all other app stages
|
||||
pub const FIRST: &str = "first";
|
||||
|
||||
/// Name of app stage that updates events. Generally this should run before UPDATE
|
||||
pub const EVENT_UPDATE: &str = "event_update";
|
||||
/// Name of app stage that runs before EVENT
|
||||
pub const PRE_EVENT: &str = "pre_events";
|
||||
|
||||
/// Name of app stage that updates events. Runs before UPDATE
|
||||
pub const EVENT: &str = "events";
|
||||
|
||||
/// Name of app stage responsible for performing setup before an update. Runs before UPDATE.
|
||||
pub const PRE_UPDATE: &str = "pre_update";
|
||||
|
@ -1,42 +1,30 @@
|
||||
use crate::converter::{convert_axis, convert_button, convert_gamepad_id};
|
||||
use bevy_app::Events;
|
||||
use bevy_ecs::{Resources, World};
|
||||
use bevy_input::prelude::*;
|
||||
use bevy_input::{gamepad::GamepadEventRaw, prelude::*};
|
||||
use gilrs::{EventType, Gilrs};
|
||||
|
||||
pub fn gilrs_event_startup_system(_world: &mut World, resources: &mut Resources) {
|
||||
let gilrs = resources.get_thread_local::<Gilrs>().unwrap();
|
||||
let mut event = resources.get_mut::<Events<GamepadEvent>>().unwrap();
|
||||
event.update();
|
||||
for (id, _) in gilrs.gamepads() {
|
||||
event.send(GamepadEvent(
|
||||
convert_gamepad_id(id),
|
||||
GamepadEventType::Connected,
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
pub fn girls_event_system(_world: &mut World, resources: &mut Resources) {
|
||||
pub fn gilrs_event_system(_world: &mut World, resources: &mut Resources) {
|
||||
let mut gilrs = resources.get_thread_local_mut::<Gilrs>().unwrap();
|
||||
let mut event = resources.get_mut::<Events<GamepadEvent>>().unwrap();
|
||||
let mut event = resources.get_mut::<Events<GamepadEventRaw>>().unwrap();
|
||||
event.update();
|
||||
while let Some(gilrs_event) = gilrs.next_event() {
|
||||
match gilrs_event.event {
|
||||
EventType::Connected => {
|
||||
event.send(GamepadEvent(
|
||||
event.send(GamepadEventRaw(
|
||||
convert_gamepad_id(gilrs_event.id),
|
||||
GamepadEventType::Connected,
|
||||
));
|
||||
}
|
||||
EventType::Disconnected => {
|
||||
event.send(GamepadEvent(
|
||||
event.send(GamepadEventRaw(
|
||||
convert_gamepad_id(gilrs_event.id),
|
||||
GamepadEventType::Disconnected,
|
||||
));
|
||||
}
|
||||
EventType::ButtonChanged(gilrs_button, value, _) => {
|
||||
if let Some(button_type) = convert_button(gilrs_button) {
|
||||
event.send(GamepadEvent(
|
||||
event.send(GamepadEventRaw(
|
||||
convert_gamepad_id(gilrs_event.id),
|
||||
GamepadEventType::ButtonChanged(button_type, value),
|
||||
));
|
||||
@ -44,7 +32,7 @@ pub fn girls_event_system(_world: &mut World, resources: &mut Resources) {
|
||||
}
|
||||
EventType::AxisChanged(gilrs_axis, value, _) => {
|
||||
if let Some(axis_type) = convert_axis(gilrs_axis) {
|
||||
event.send(GamepadEvent(
|
||||
event.send(GamepadEventRaw(
|
||||
convert_gamepad_id(gilrs_event.id),
|
||||
GamepadEventType::AxisChanged(axis_type, value),
|
||||
));
|
||||
|
@ -4,7 +4,7 @@ mod gilrs_system;
|
||||
use bevy_app::prelude::*;
|
||||
use bevy_ecs::prelude::*;
|
||||
use gilrs::GilrsBuilder;
|
||||
use gilrs_system::{gilrs_event_startup_system, girls_event_system};
|
||||
use gilrs_system::gilrs_event_system;
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct GilrsPlugin;
|
||||
@ -18,8 +18,11 @@ impl Plugin for GilrsPlugin {
|
||||
{
|
||||
Ok(gilrs) => {
|
||||
app.add_thread_local_resource(gilrs)
|
||||
.add_startup_system(gilrs_event_startup_system.thread_local_system())
|
||||
.add_system_to_stage(stage::FIRST, girls_event_system.thread_local_system());
|
||||
.add_startup_system(gilrs_event_system.thread_local_system())
|
||||
.add_system_to_stage(
|
||||
stage::PRE_EVENT,
|
||||
gilrs_event_system.thread_local_system(),
|
||||
);
|
||||
}
|
||||
Err(err) => log::error!("Failed to start Gilrs. {}", err),
|
||||
}
|
||||
|
@ -20,6 +20,10 @@ pub enum GamepadEventType {
|
||||
#[cfg_attr(feature = "serialize", derive(serde::Serialize, serde::Deserialize))]
|
||||
pub struct GamepadEvent(pub Gamepad, pub GamepadEventType);
|
||||
|
||||
#[derive(Debug, Clone, PartialEq)]
|
||||
#[cfg_attr(feature = "serialize", derive(serde::Serialize, serde::Deserialize))]
|
||||
pub struct GamepadEventRaw(pub Gamepad, pub GamepadEventType);
|
||||
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
|
||||
#[cfg_attr(feature = "serialize", derive(serde::Serialize, serde::Deserialize))]
|
||||
pub enum GamepadButtonType {
|
||||
@ -66,51 +70,51 @@ pub enum GamepadAxisType {
|
||||
pub struct GamepadAxis(pub Gamepad, pub GamepadAxisType);
|
||||
|
||||
#[derive(Default, Debug)]
|
||||
pub struct GamepadSetting {
|
||||
pub default_button_setting: ButtonSetting,
|
||||
pub default_axis_setting: AxisSetting,
|
||||
pub default_button_axis_setting: ButtonAxisSetting,
|
||||
pub button_settings: HashMap<GamepadButton, ButtonSetting>,
|
||||
pub axis_settings: HashMap<GamepadAxis, AxisSetting>,
|
||||
pub button_axis_settings: HashMap<GamepadButton, ButtonAxisSetting>,
|
||||
pub struct GamepadSettings {
|
||||
pub default_button_settings: ButtonSettings,
|
||||
pub default_axis_settings: AxisSettings,
|
||||
pub default_button_axis_settings: ButtonAxisSettings,
|
||||
pub button_settings: HashMap<GamepadButton, ButtonSettings>,
|
||||
pub axis_settings: HashMap<GamepadAxis, AxisSettings>,
|
||||
pub button_axis_settings: HashMap<GamepadButton, ButtonAxisSettings>,
|
||||
}
|
||||
|
||||
impl GamepadSetting {
|
||||
pub fn get_button_setting(&self, button: GamepadButton) -> &ButtonSetting {
|
||||
impl GamepadSettings {
|
||||
pub fn get_button_settings(&self, button: GamepadButton) -> &ButtonSettings {
|
||||
self.button_settings
|
||||
.get(&button)
|
||||
.unwrap_or(&self.default_button_setting)
|
||||
.unwrap_or(&self.default_button_settings)
|
||||
}
|
||||
|
||||
pub fn get_axis_setting(&self, axis: GamepadAxis) -> &AxisSetting {
|
||||
pub fn get_axis_settings(&self, axis: GamepadAxis) -> &AxisSettings {
|
||||
self.axis_settings
|
||||
.get(&axis)
|
||||
.unwrap_or(&self.default_axis_setting)
|
||||
.unwrap_or(&self.default_axis_settings)
|
||||
}
|
||||
|
||||
pub fn get_button_axis_setting(&self, button: GamepadButton) -> &ButtonAxisSetting {
|
||||
pub fn get_button_axis_settings(&self, button: GamepadButton) -> &ButtonAxisSettings {
|
||||
self.button_axis_settings
|
||||
.get(&button)
|
||||
.unwrap_or(&self.default_button_axis_setting)
|
||||
.unwrap_or(&self.default_button_axis_settings)
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct ButtonSetting {
|
||||
pub struct ButtonSettings {
|
||||
pub press: f32,
|
||||
pub release: f32,
|
||||
}
|
||||
|
||||
impl Default for ButtonSetting {
|
||||
impl Default for ButtonSettings {
|
||||
fn default() -> Self {
|
||||
ButtonSetting {
|
||||
ButtonSettings {
|
||||
press: 0.75,
|
||||
release: 0.65,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl ButtonSetting {
|
||||
impl ButtonSettings {
|
||||
fn is_pressed(&self, value: f32) -> bool {
|
||||
value >= self.press
|
||||
}
|
||||
@ -121,7 +125,7 @@ impl ButtonSetting {
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct AxisSetting {
|
||||
pub struct AxisSettings {
|
||||
pub positive_high: f32,
|
||||
pub positive_low: f32,
|
||||
pub negative_high: f32,
|
||||
@ -129,9 +133,9 @@ pub struct AxisSetting {
|
||||
pub threshold: f32,
|
||||
}
|
||||
|
||||
impl Default for AxisSetting {
|
||||
impl Default for AxisSettings {
|
||||
fn default() -> Self {
|
||||
AxisSetting {
|
||||
AxisSettings {
|
||||
positive_high: 0.95,
|
||||
positive_low: 0.05,
|
||||
negative_high: -0.95,
|
||||
@ -141,7 +145,7 @@ impl Default for AxisSetting {
|
||||
}
|
||||
}
|
||||
|
||||
impl AxisSetting {
|
||||
impl AxisSettings {
|
||||
fn filter(&self, new_value: f32, old_value: Option<f32>) -> f32 {
|
||||
if let Some(old_value) = old_value {
|
||||
if (new_value - old_value).abs() <= self.threshold {
|
||||
@ -162,15 +166,15 @@ impl AxisSetting {
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct ButtonAxisSetting {
|
||||
pub struct ButtonAxisSettings {
|
||||
pub high: f32,
|
||||
pub low: f32,
|
||||
pub threshold: f32,
|
||||
}
|
||||
|
||||
impl Default for ButtonAxisSetting {
|
||||
impl Default for ButtonAxisSettings {
|
||||
fn default() -> Self {
|
||||
ButtonAxisSetting {
|
||||
ButtonAxisSettings {
|
||||
high: 0.95,
|
||||
low: 0.05,
|
||||
threshold: 0.01,
|
||||
@ -178,7 +182,7 @@ impl Default for ButtonAxisSetting {
|
||||
}
|
||||
}
|
||||
|
||||
impl ButtonAxisSetting {
|
||||
impl ButtonAxisSettings {
|
||||
fn filter(&self, new_value: f32, old_value: Option<f32>) -> f32 {
|
||||
if let Some(old_value) = old_value {
|
||||
if (new_value - old_value).abs() <= self.threshold {
|
||||
@ -195,58 +199,73 @@ impl ButtonAxisSetting {
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct GamepadEventState {
|
||||
gamepad_event_reader: EventReader<GamepadEvent>,
|
||||
}
|
||||
|
||||
#[allow(clippy::float_cmp)]
|
||||
pub fn gamepad_event_system(
|
||||
mut state: Local<GamepadEventState>,
|
||||
mut event_reader: Local<EventReader<GamepadEventRaw>>,
|
||||
mut button_input: ResMut<Input<GamepadButton>>,
|
||||
mut axis: ResMut<Axis<GamepadAxis>>,
|
||||
mut button_axis: ResMut<Axis<GamepadButton>>,
|
||||
events: Res<Events<GamepadEvent>>,
|
||||
settings: Res<GamepadSetting>,
|
||||
raw_events: Res<Events<GamepadEventRaw>>,
|
||||
mut events: ResMut<Events<GamepadEvent>>,
|
||||
settings: Res<GamepadSettings>,
|
||||
) {
|
||||
button_input.update();
|
||||
for event in state.gamepad_event_reader.iter(&events) {
|
||||
let (gamepad, event) = (&event.0, &event.1);
|
||||
for event in event_reader.iter(&raw_events) {
|
||||
let (gamepad, event) = (event.0, &event.1);
|
||||
match event {
|
||||
GamepadEventType::Connected => {
|
||||
events.send(GamepadEvent(gamepad, event.clone()));
|
||||
for button_type in ALL_BUTTON_TYPES.iter() {
|
||||
let gamepad_button = GamepadButton(*gamepad, *button_type);
|
||||
let gamepad_button = GamepadButton(gamepad, *button_type);
|
||||
button_input.reset(gamepad_button);
|
||||
button_axis.set(gamepad_button, 0.0);
|
||||
}
|
||||
for axis_type in ALL_AXIS_TYPES.iter() {
|
||||
axis.set(GamepadAxis(*gamepad, *axis_type), 0.0);
|
||||
axis.set(GamepadAxis(gamepad, *axis_type), 0.0);
|
||||
}
|
||||
}
|
||||
GamepadEventType::Disconnected => {
|
||||
events.send(GamepadEvent(gamepad, event.clone()));
|
||||
for button_type in ALL_BUTTON_TYPES.iter() {
|
||||
let gamepad_button = GamepadButton(*gamepad, *button_type);
|
||||
let gamepad_button = GamepadButton(gamepad, *button_type);
|
||||
button_input.reset(gamepad_button);
|
||||
button_axis.remove(gamepad_button);
|
||||
}
|
||||
for axis_type in ALL_AXIS_TYPES.iter() {
|
||||
axis.remove(GamepadAxis(*gamepad, *axis_type));
|
||||
axis.remove(GamepadAxis(gamepad, *axis_type));
|
||||
}
|
||||
}
|
||||
GamepadEventType::AxisChanged(axis_type, value) => {
|
||||
let gamepad_axis = GamepadAxis(*gamepad, *axis_type);
|
||||
let value = settings
|
||||
.get_axis_setting(gamepad_axis)
|
||||
.filter(*value, axis.get(gamepad_axis));
|
||||
axis.set(gamepad_axis, value);
|
||||
let gamepad_axis = GamepadAxis(gamepad, *axis_type);
|
||||
let old_value = axis.get(gamepad_axis);
|
||||
let filtered_value = settings
|
||||
.get_axis_settings(gamepad_axis)
|
||||
.filter(*value, old_value);
|
||||
axis.set(gamepad_axis, filtered_value);
|
||||
|
||||
// only send event if axis has changed after going through filters
|
||||
if let Some(old_value) = old_value {
|
||||
if old_value == filtered_value {
|
||||
return;
|
||||
}
|
||||
} else if filtered_value == 0.0 {
|
||||
return;
|
||||
}
|
||||
|
||||
events.send(GamepadEvent(
|
||||
gamepad,
|
||||
GamepadEventType::AxisChanged(*axis_type, filtered_value),
|
||||
))
|
||||
}
|
||||
GamepadEventType::ButtonChanged(button_type, value) => {
|
||||
let gamepad_button = GamepadButton(*gamepad, *button_type);
|
||||
let gamepad_button = GamepadButton(gamepad, *button_type);
|
||||
let old_value = button_axis.get(gamepad_button);
|
||||
let filtered_value = settings
|
||||
.get_button_axis_setting(gamepad_button)
|
||||
.filter(*value, button_axis.get(gamepad_button));
|
||||
.get_button_axis_settings(gamepad_button)
|
||||
.filter(*value, old_value);
|
||||
button_axis.set(gamepad_button, filtered_value);
|
||||
|
||||
let button_property = settings.get_button_setting(gamepad_button);
|
||||
let button_property = settings.get_button_settings(gamepad_button);
|
||||
if button_input.pressed(gamepad_button) {
|
||||
if button_property.is_released(*value) {
|
||||
button_input.release(gamepad_button);
|
||||
@ -254,6 +273,20 @@ pub fn gamepad_event_system(
|
||||
} else if button_property.is_pressed(*value) {
|
||||
button_input.press(gamepad_button);
|
||||
}
|
||||
|
||||
// only send event if axis has changed after going through filters
|
||||
if let Some(old_value) = old_value {
|
||||
if old_value == filtered_value {
|
||||
return;
|
||||
}
|
||||
} else if filtered_value == 0.0 {
|
||||
return;
|
||||
}
|
||||
|
||||
events.send(GamepadEvent(
|
||||
gamepad,
|
||||
GamepadEventType::ButtonChanged(*button_type, filtered_value),
|
||||
))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -27,7 +27,10 @@ use mouse::{mouse_button_input_system, MouseButton, MouseButtonInput, MouseMotio
|
||||
use touch::{touch_screen_input_system, TouchInput, Touches};
|
||||
|
||||
use bevy_ecs::IntoQuerySystem;
|
||||
use gamepad::{gamepad_event_system, GamepadAxis, GamepadButton, GamepadEvent, GamepadSetting};
|
||||
use gamepad::{
|
||||
gamepad_event_system, GamepadAxis, GamepadButton, GamepadEvent, GamepadEventRaw,
|
||||
GamepadSettings,
|
||||
};
|
||||
|
||||
/// Adds keyboard and mouse input to an App
|
||||
#[derive(Default)]
|
||||
@ -40,30 +43,18 @@ impl Plugin for InputPlugin {
|
||||
.add_event::<MouseMotion>()
|
||||
.add_event::<MouseWheel>()
|
||||
.init_resource::<Input<KeyCode>>()
|
||||
.add_system_to_stage(
|
||||
bevy_app::stage::EVENT_UPDATE,
|
||||
keyboard_input_system.system(),
|
||||
)
|
||||
.add_system_to_stage(bevy_app::stage::EVENT, keyboard_input_system.system())
|
||||
.init_resource::<Input<MouseButton>>()
|
||||
.add_system_to_stage(
|
||||
bevy_app::stage::EVENT_UPDATE,
|
||||
mouse_button_input_system.system(),
|
||||
)
|
||||
.add_system_to_stage(bevy_app::stage::EVENT, mouse_button_input_system.system())
|
||||
.add_event::<GamepadEvent>()
|
||||
.init_resource::<GamepadSetting>()
|
||||
.add_event::<GamepadEventRaw>()
|
||||
.init_resource::<GamepadSettings>()
|
||||
.init_resource::<Input<GamepadButton>>()
|
||||
.init_resource::<Axis<GamepadAxis>>()
|
||||
.init_resource::<Axis<GamepadButton>>()
|
||||
.add_startup_system_to_stage(
|
||||
bevy_app::startup_stage::POST_STARTUP,
|
||||
gamepad_event_system.system(),
|
||||
)
|
||||
.add_system_to_stage(bevy_app::stage::EVENT_UPDATE, gamepad_event_system.system())
|
||||
.add_system_to_stage(bevy_app::stage::EVENT, gamepad_event_system.system())
|
||||
.add_event::<TouchInput>()
|
||||
.init_resource::<Touches>()
|
||||
.add_system_to_stage(
|
||||
bevy_app::stage::EVENT_UPDATE,
|
||||
touch_screen_input_system.system(),
|
||||
);
|
||||
.add_system_to_stage(bevy_app::stage::EVENT, touch_screen_input_system.system());
|
||||
}
|
||||
}
|
||||
|
@ -30,7 +30,7 @@ impl Plugin for ScenePlugin {
|
||||
.add_asset::<Scene>()
|
||||
.init_asset_loader::<SceneLoader>()
|
||||
.init_resource::<SceneSpawner>()
|
||||
.add_stage_after(stage::EVENT_UPDATE, SCENE_STAGE)
|
||||
.add_stage_after(stage::EVENT, SCENE_STAGE)
|
||||
.add_system_to_stage(SCENE_STAGE, scene_spawner_system.thread_local_system());
|
||||
}
|
||||
}
|
||||
|
@ -40,32 +40,25 @@ fn gamepad_system(
|
||||
button_axes: Res<Axis<GamepadButton>>,
|
||||
axes: Res<Axis<GamepadAxis>>,
|
||||
) {
|
||||
for gamepad in lobby.gamepads.iter() {
|
||||
let south_button = GamepadButton(*gamepad, GamepadButtonType::South);
|
||||
if button_inputs.just_pressed(south_button) {
|
||||
println!(
|
||||
"{:?} of {:?} is just pressed",
|
||||
GamepadButtonType::South,
|
||||
gamepad
|
||||
);
|
||||
} else if button_inputs.just_released(south_button) {
|
||||
println!(
|
||||
"{:?} of {:?} is just released",
|
||||
GamepadButtonType::South,
|
||||
gamepad
|
||||
);
|
||||
for gamepad in lobby.gamepads.iter().cloned() {
|
||||
if button_inputs.just_pressed(GamepadButton(gamepad, GamepadButtonType::South)) {
|
||||
println!("{:?} just pressed South", gamepad);
|
||||
} else if button_inputs.just_released(GamepadButton(gamepad, GamepadButtonType::South)) {
|
||||
println!("{:?} just released South", gamepad);
|
||||
}
|
||||
|
||||
println!(
|
||||
"For {:?}: {:?} is {:.4}, {:?} is {:.4}",
|
||||
gamepad,
|
||||
GamepadButtonType::RightTrigger2,
|
||||
button_axes
|
||||
.get(GamepadButton(*gamepad, GamepadButtonType::RightTrigger2))
|
||||
.unwrap_or(0.0),
|
||||
GamepadAxisType::LeftStickX,
|
||||
axes.get(GamepadAxis(*gamepad, GamepadAxisType::LeftStickX))
|
||||
.unwrap_or(0.0)
|
||||
)
|
||||
let right_trigger = button_axes
|
||||
.get(GamepadButton(gamepad, GamepadButtonType::RightTrigger2))
|
||||
.unwrap();
|
||||
if right_trigger.abs() > 0.01 {
|
||||
println!("{:?} RightTrigger2 value is {}", gamepad, right_trigger);
|
||||
}
|
||||
|
||||
let left_stick_x = axes
|
||||
.get(GamepadAxis(gamepad, GamepadAxisType::LeftStickX))
|
||||
.unwrap();
|
||||
if left_stick_x.abs() > 0.01 {
|
||||
println!("{:?} LeftStickX value is {}", gamepad, left_stick_x);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -4,18 +4,15 @@ use bevy_input::gamepad::{GamepadEvent, GamepadEventType};
|
||||
fn main() {
|
||||
App::build()
|
||||
.add_default_plugins()
|
||||
.add_startup_system(gamepad_raw_events.system())
|
||||
.add_system(gamepad_raw_events.system())
|
||||
.add_system(gamepad_events.system())
|
||||
.run();
|
||||
}
|
||||
|
||||
#[derive(Default)]
|
||||
struct State {
|
||||
gamepad_event_reader: EventReader<GamepadEvent>,
|
||||
}
|
||||
|
||||
fn gamepad_raw_events(mut state: Local<State>, gamepad_event: Res<Events<GamepadEvent>>) {
|
||||
for event in state.gamepad_event_reader.iter(&gamepad_event) {
|
||||
fn gamepad_events(
|
||||
mut event_reader: Local<EventReader<GamepadEvent>>,
|
||||
gamepad_event: Res<Events<GamepadEvent>>,
|
||||
) {
|
||||
for event in event_reader.iter(&gamepad_event) {
|
||||
match &event {
|
||||
GamepadEvent(gamepad, GamepadEventType::Connected) => {
|
||||
println!("{:?} Connected", gamepad);
|
Loading…
Reference in New Issue
Block a user