use super::{DemuxMode, DemuxOutput, helpers};
use evdev::InputEvent;
use gilrs::{Event, EventType, GamepadId, Gilrs};
pub struct MulticastMode;
impl MulticastMode {
fn convert_event(event: &Event, primary: gilrs::Gamepad) -> Option<Vec<InputEvent>> {
match event.event {
EventType::ButtonPressed(btn, _) | EventType::ButtonReleased(btn, _) => {
let is_pressed = matches!(event.event, EventType::ButtonPressed(..));
helpers::create_button_key_event(btn, is_pressed).map(|e| vec![e])
}
EventType::ButtonChanged(btn, _, _) => {
let abs_axis = crate::utils::evdev::gilrs_button_to_evdev_axis(btn)?;
Some(vec![helpers::process_button_axis(btn, &primary, abs_axis)])
}
EventType::AxisChanged(axis, raw_val, _) => {
helpers::create_stick_event(axis, raw_val).map(|e| vec![e])
}
_ => None,
}
}
}
impl DemuxMode for MulticastMode {
fn handle_event(
&mut self,
event: &Event,
primary_id: GamepadId,
virtuals: usize,
gilrs: &Gilrs,
) -> Option<DemuxOutput> {
if event.id != primary_id {
return None;
}
let primary = gilrs.gamepad(primary_id);
Self::convert_event(event, primary).map(|events| {
let distributed = (0..virtuals).map(|idx| (idx, events.clone())).collect();
DemuxOutput::events(distributed)
})
}
fn initial_active_virtuals(&self, virtuals: usize) -> Vec<usize> {
(0..virtuals).collect()
}
}