Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 14 additions & 2 deletions rootfs/usr/share/inputplumber/profiles/mouse_keyboard_wasd.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -177,12 +177,24 @@ mapping:
button: RightBumper
target_events:
- mouse:
button: WheelUp
wheel:
name: Vertical
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What value is the name attribute providing? I.e. I can't have a horizontal up or vertical left? Plane is essentially assumed.

Didn't you want to combine the Mouse:Wheel:Vertical and Mouse:Wheel:Horizontal into a single Mouse:Wheel represented by a Vector2?

direction: up
#- mouse:
# wheel:
# name: Horizontal
# direction: right

- name: LB
source_event:
gamepad:
button: LeftBumper
target_events:
- mouse:
button: WheelDown
wheel:
name: Vertical
direction: down
#- mouse:
# wheel:
# name: Horizontal
# direction: left
8 changes: 8 additions & 0 deletions src/config/capability_map.rs
Original file line number Diff line number Diff line change
Expand Up @@ -275,6 +275,7 @@ pub struct MouseCapability {
pub button: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub motion: Option<MouseMotionCapability>,
pub wheel: Option<MouseWheelCapability>,
}

#[derive(Debug, Deserialize, Serialize, Clone, JsonSchema, PartialEq)]
Expand All @@ -286,6 +287,13 @@ pub struct MouseMotionCapability {
pub speed_pps: Option<u64>,
}

#[derive(Debug, Deserialize, Serialize, Clone, JsonSchema, PartialEq)]
#[serde(rename_all = "snake_case")]
pub struct MouseWheelCapability {
pub name: String,
pub direction: Option<String>,
}

#[derive(Debug, Deserialize, Serialize, Clone, JsonSchema, PartialEq)]
#[serde(rename_all = "snake_case")]
pub struct TouchpadCapability {
Expand Down
20 changes: 2 additions & 18 deletions src/dbus/interface/composite_device.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ use crate::{
config::DeviceProfile,
dbus::polkit::check_polkit,
input::{
capability::{Capability, Gamepad, Mouse},
capability::Capability,
composite_device::{client::CompositeDeviceClient, InterceptMode},
event::{native::NativeEvent, value::InputValue},
},
Expand Down Expand Up @@ -465,23 +465,7 @@ impl CompositeDeviceInterface {

let mut capability_strings = HashSet::new();
for cap in capabilities {
let str = match cap {
Capability::Gamepad(gamepad) => match gamepad {
Gamepad::Button(button) => format!("Gamepad:Button:{}", button),
Gamepad::Axis(axis) => format!("Gamepad:Axis:{}", axis),
Gamepad::Trigger(trigger) => format!("Gamepad:Trigger:{}", trigger),
Gamepad::Accelerometer => "Gamepad:Accelerometer".to_string(),
Gamepad::Gyro => "Gamepad:Gyro".to_string(),
Gamepad::Dial(dial) => format!("Gamepad:Dial:{dial}"),
},
Capability::Mouse(mouse) => match mouse {
Mouse::Motion => "Mouse:Motion".to_string(),
Mouse::Button(button) => format!("Mouse:Button:{}", button),
},
Capability::Keyboard(key) => format!("Keyboard:{}", key),
Capability::DBus(action) => format!("DBus:{}", action.as_str()),
_ => cap.to_string(),
};
let str = cap.to_capability_string();
capability_strings.insert(str);
}

Expand Down
14 changes: 10 additions & 4 deletions src/drivers/lego/driver.rs
Original file line number Diff line number Diff line change
Expand Up @@ -162,9 +162,9 @@ impl Driver {
let input_report = XInputDataReport::unpack(&buf)?;

// Print input report for debugging
//log::trace!("--- Input report ---");
//log::trace!("{input_report}");
//log::trace!(" ---- End Report ----");
//log::debug!("--- Input report ---");
//log::debug!("{input_report}");
//log::debug!(" ---- End Report ----");

// Update the state
let old_dinput_state = self.update_xinput_state(input_report);
Expand Down Expand Up @@ -408,8 +408,14 @@ impl Driver {
})));
}
if state.mouse_z != old_state.mouse_z {
let value = state.mouse_z.wrapping_sub(128) as i8;
let value = match value {
127 => -1,
v => v,
};

events.push(Event::Trigger(TriggerEvent::MouseWheel(MouseWheelInput {
value: state.mouse_z,
value,
})));
}

Expand Down
4 changes: 2 additions & 2 deletions src/drivers/lego/hid_report.rs
Original file line number Diff line number Diff line change
Expand Up @@ -434,8 +434,8 @@ pub struct XInputDataReport {
#[packed_field(bytes = "24")]
pub unk_23: u8,

#[packed_field(bytes = "25")]
pub mouse_z: i8,
#[packed_field(bytes = "25", endian = "lsb")]
pub mouse_z: u8,

#[packed_field(bytes = "26..=27", endian = "msb")]
pub touch_x: u16,
Expand Down
1 change: 0 additions & 1 deletion src/drivers/lego/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ const HID_TIMEOUT: i32 = 10;
const XINPUT_COMMAND_ID: u8 = 0x74;

// Input report axis ranges
pub const MOUSE_WHEEL_MAX: f64 = 120.0;
pub const PAD_FORCE_MAX: f64 = 127.0;
pub const PAD_FORCE_NORMAL: u8 = 32; /* Simulated average pressure */
pub const PAD_X_MAX: f64 = 1024.0;
Expand Down
42 changes: 42 additions & 0 deletions src/input/capability.rs
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ impl Capability {
Capability::Mouse(mouse) => match mouse {
Mouse::Motion => "Mouse:Motion".to_string(),
Mouse::Button(button) => format!("Mouse:Button:{button}"),
Mouse::Wheel(wheel) => format!("Mouse:Wheel:{wheel}"),
},
Capability::Keyboard(key) => format!("Keyboard:{key}"),
Capability::None => "None".to_string(),
Expand Down Expand Up @@ -267,6 +268,15 @@ impl From<CapabilityConfig> for Capability {
let button = button.unwrap();
return Capability::Mouse(Mouse::Button(button));
}

// Wheel
if let Some(wheel) = mouse.wheel.as_ref() {
let Ok(wheel) = MouseWheel::from_str(&wheel.name) else {
log::error!("Invalid or unimplemented wheel: {}", wheel.name);
return Capability::NotImplemented;
};
return Capability::Mouse(Mouse::Wheel(wheel));
}
}

// DBus
Expand Down Expand Up @@ -437,13 +447,16 @@ pub enum Mouse {
Motion,
/// Mouse Buttons are typically binary mouse input that represents button presses
Button(MouseButton),
/// Mouse wheel input is relative
Wheel(MouseWheel),
}

impl fmt::Display for Mouse {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
match self {
Mouse::Motion => write!(f, "Motion"),
Mouse::Button(_) => write!(f, "Button"),
Mouse::Wheel(_) => write!(f, "Wheel"),
}
}
}
Expand Down Expand Up @@ -523,6 +536,35 @@ impl FromStr for MouseButton {
}
}

#[derive(Clone, Debug, PartialEq, Eq, Hash)]
pub enum MouseWheel {
// Mouse wheel up or down
Vertical,
// Mouse wheel left or right
Horizontal,
}

impl fmt::Display for MouseWheel {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
match self {
MouseWheel::Vertical => write!(f, "Vertical"),
MouseWheel::Horizontal => write!(f, "Horizontal"),
}
}
}

impl FromStr for MouseWheel {
type Err = ();

fn from_str(s: &str) -> Result<Self, Self::Err> {
match s {
"Vertical" => Ok(MouseWheel::Vertical),
"Horizontal" => Ok(MouseWheel::Horizontal),
_ => Err(()),
}
}
}

/// Gamepad Buttons typically use binary input that represents button presses
#[derive(Clone, Debug, PartialEq, Eq, Hash)]
pub enum GamepadButton {
Expand Down
14 changes: 6 additions & 8 deletions src/input/composite_device/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -988,6 +988,7 @@ impl CompositeDevice {
continue;
}
}
Mouse::Wheel(_) => {}
},
Capability::Touchscreen(_) => (),
Capability::Gyroscope(_) => (),
Expand Down Expand Up @@ -1933,16 +1934,16 @@ impl CompositeDevice {
fn is_new_active_event(&mut self, cap: &Capability, is_pressed: bool) -> bool {
let active = self.active_inputs.contains(cap);
if is_pressed && !active {
log::debug!("New active capability: {cap:?}");
log::trace!("New active capability: {cap:?}");
self.active_inputs.push(cap.clone());
}
// Ignore up events for actions we've already handled.
if !is_pressed && !active {
log::debug!("Blocked up event for capability: {cap:?}");
log::trace!("Blocked up event for capability: {cap:?}");
return false;
}
if !is_pressed && active {
log::debug!("Removed inactive capability: {cap:?}");
log::trace!("Removed inactive capability: {cap:?}");
let index = self.active_inputs.iter().position(|r| r == cap).unwrap();
self.active_inputs.remove(index);
}
Expand All @@ -1956,12 +1957,12 @@ impl CompositeDevice {
intercept: bool,
) -> Result<bool, Box<dyn Error>> {
if self.intercept_activation_caps.len() == 1 {
log::debug!("Checking single intercept event.");
log::trace!("Checking single intercept event.");
return self
.is_intercept_event_single(event, is_pressed, intercept)
.await;
}
log::debug!("Checking multi intercept event.");
log::trace!("Checking multi intercept event.");
self.is_intercept_event_multi(event, is_pressed, intercept)
.await
}
Expand All @@ -1976,7 +1977,6 @@ impl CompositeDevice {
// Check if we have met the criteria for InterceptMode:Always
if intercept && self.intercept_activation_caps.contains(&cap) && is_pressed {
log::debug!("Found matching intercept event: {:?}", cap);
log::debug!("It is a DOWN event!");
// Stop here if this is a repeat event.
if self.intercept_active_inputs.contains(&cap) {
log::debug!("The event is already in the list. Skipping.");
Expand All @@ -1999,8 +1999,6 @@ impl CompositeDevice {
{
// Check if we already sent the intercept event. We might not be in the same intercept mode
// so dont check intercept.
log::debug!("It is an UP event!");

log::trace!("Remove from intercept active inputs: {cap:?}");
let index = self
.intercept_active_inputs
Expand Down
16 changes: 15 additions & 1 deletion src/input/event/evdev.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ use evdev::{AbsInfo, AbsoluteAxisCode, EventType, InputEvent, KeyCode, RelativeA

use crate::input::capability::{
Capability, Gamepad, GamepadAxis, GamepadButton, GamepadDial, GamepadTrigger, Keyboard, Mouse,
MouseButton, Touch, TouchButton, Touchpad,
MouseButton, MouseWheel, Touch, TouchButton, Touchpad,
};

use super::{native::NativeEvent, value::InputValue};
Expand Down Expand Up @@ -465,6 +465,12 @@ impl EvdevEvent {
EventType::RELATIVE => match RelativeAxisCode(code) {
RelativeAxisCode::REL_X => Capability::Mouse(Mouse::Motion),
RelativeAxisCode::REL_Y => Capability::Mouse(Mouse::Motion),
RelativeAxisCode::REL_WHEEL => {
Capability::Mouse(Mouse::Wheel(MouseWheel::Vertical))
}
RelativeAxisCode::REL_HWHEEL => {
Capability::Mouse(Mouse::Wheel(MouseWheel::Horizontal))
}
_ => Capability::NotImplemented,
},
EventType::MISC => Capability::NotImplemented,
Expand Down Expand Up @@ -561,6 +567,7 @@ fn event_type_from_capability(capability: Capability) -> Option<EventType> {
Capability::Mouse(mouse) => match mouse {
Mouse::Motion => Some(EventType::RELATIVE),
Mouse::Button(_) => Some(EventType::KEY),
Mouse::Wheel(_) => Some(EventType::RELATIVE),
},
Capability::Gamepad(gamepad) => match gamepad {
Gamepad::Button(button) => match button {
Expand Down Expand Up @@ -701,6 +708,11 @@ fn event_codes_from_capability(capability: Capability) -> Vec<u16> {
MouseButton::Extra => vec![KeyCode::BTN_EXTRA.0],
MouseButton::Side => vec![KeyCode::BTN_SIDE.0],
},

Mouse::Wheel(wheel) => match wheel {
MouseWheel::Vertical => vec![RelativeAxisCode::REL_WHEEL.0],
MouseWheel::Horizontal => vec![RelativeAxisCode::REL_HWHEEL.0],
},
},
Capability::Keyboard(key) => match key {
Keyboard::Key0 => vec![KeyCode::KEY_0.0],
Expand Down Expand Up @@ -975,6 +987,8 @@ fn input_event_from_value(
EventType::RELATIVE => match RelativeAxisCode(code) {
RelativeAxisCode::REL_X => x.map(|v| v as i32),
RelativeAxisCode::REL_Y => y.map(|v| v as i32),
RelativeAxisCode::REL_HWHEEL => x.map(|v| v as i32),
RelativeAxisCode::REL_WHEEL => y.map(|v| v as i32),
_ => None,
},
_ => None,
Expand Down
Loading