Added analog stick remapping to keys
This commit is contained in:
parent
c83b70a91a
commit
c838c55af2
2 changed files with 186 additions and 82 deletions
|
@ -88,23 +88,45 @@ impl Config {
|
|||
modifiers.axis.insert(modmap, map.clone());
|
||||
}
|
||||
|
||||
let mut pad_horizontal: Vec<Key> = bindings.axis.get("BTN_DPAD_LEFT")
|
||||
let mut pad_x: Vec<Key> = bindings.axis.get("BTN_DPAD_LEFT")
|
||||
.unwrap_or(&Vec::new()).clone();
|
||||
pad_horizontal.extend(bindings.axis.get("BTN_DPAD_RIGHT")
|
||||
pad_x.extend(bindings.axis.get("BTN_DPAD_RIGHT")
|
||||
.unwrap_or(&Vec::new()));
|
||||
let mut pad_vertical: Vec<Key> = bindings.axis.get("BTN_DPAD_UP")
|
||||
let mut pad_y: Vec<Key> = bindings.axis.get("BTN_DPAD_UP")
|
||||
.unwrap_or(&Vec::new()).clone();
|
||||
pad_vertical.extend(bindings.axis.get("BTN_DPAD_DOWN")
|
||||
pad_y.extend(bindings.axis.get("BTN_DPAD_DOWN")
|
||||
.unwrap_or(&Vec::new()));
|
||||
bindings.axis.insert("NONE_X".to_string(), pad_horizontal);
|
||||
bindings.axis.insert("NONE_Y".to_string(), pad_vertical);
|
||||
bindings.axis.insert("NONE_X".to_string(), pad_x);
|
||||
bindings.axis.insert("NONE_Y".to_string(), pad_y);
|
||||
|
||||
let mut lstick_x: Vec<Key> = bindings.axis.get("LSTICK_LEFT")
|
||||
.unwrap_or(&Vec::new()).clone();
|
||||
lstick_x.extend(bindings.axis.get("LSTICK_RIGHT")
|
||||
.unwrap_or(&Vec::new()));
|
||||
let mut lstick_y: Vec<Key> = bindings.axis.get("LSTICK_UP")
|
||||
.unwrap_or(&Vec::new()).clone();
|
||||
lstick_y.extend(bindings.axis.get("LSTICK_DOWN")
|
||||
.unwrap_or(&Vec::new()));
|
||||
bindings.axis.insert("LSTICK_X".to_string(), lstick_x);
|
||||
bindings.axis.insert("LSTICK_Y".to_string(), lstick_y);
|
||||
|
||||
let mut rstick_x: Vec<Key> = bindings.axis.get("RSTICK_LEFT")
|
||||
.unwrap_or(&Vec::new()).clone();
|
||||
rstick_x.extend(bindings.axis.get("RSTICK_RIGHT")
|
||||
.unwrap_or(&Vec::new()));
|
||||
let mut rstick_y: Vec<Key> = bindings.axis.get("RSTICK_UP")
|
||||
.unwrap_or(&Vec::new()).clone();
|
||||
rstick_y.extend(bindings.axis.get("RSTICK_DOWN")
|
||||
.unwrap_or(&Vec::new()));
|
||||
bindings.axis.insert("RSTICK_X".to_string(), rstick_x);
|
||||
bindings.axis.insert("RSTICK_Y".to_string(), rstick_y);
|
||||
|
||||
Self {
|
||||
name: file_name,
|
||||
bindings: bindings,
|
||||
combinations: combinations,
|
||||
modifiers: modifiers,
|
||||
settings: settings,
|
||||
bindings,
|
||||
combinations,
|
||||
modifiers,
|
||||
settings,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,21 +6,25 @@ use crate::virtual_devices::VirtualDevices;
|
|||
use crate::Config;
|
||||
use crate::active_client::*;
|
||||
|
||||
struct Settings {
|
||||
cursor_analog_mode: String,
|
||||
scroll_analog_mode: String,
|
||||
cursor_sensitivity: u64,
|
||||
scroll_sensitivity: u64,
|
||||
has_signed_axis_value: bool,
|
||||
|
||||
struct Stick {
|
||||
function: String,
|
||||
sensitivity: u64,
|
||||
deadzone: i32,
|
||||
}
|
||||
|
||||
struct Settings {
|
||||
lstick: Stick,
|
||||
rstick: Stick,
|
||||
axis_16_bit: bool,
|
||||
}
|
||||
|
||||
pub struct EventReader {
|
||||
config: HashMap<String, Config>,
|
||||
stream: Arc<Mutex<EventStream>>,
|
||||
virt_dev: Arc<Mutex<VirtualDevices>>,
|
||||
cursor_analog_position: Arc<Mutex<Vec<i32>>>,
|
||||
scroll_analog_position: Arc<Mutex<Vec<i32>>>,
|
||||
lstick_position: Arc<Mutex<Vec<i32>>>,
|
||||
rstick_position: Arc<Mutex<Vec<i32>>>,
|
||||
modifiers: Arc<Mutex<BTreeMap<Key, i32>>>,
|
||||
device_is_connected: Arc<Mutex<bool>>,
|
||||
current_desktop: Option<String>,
|
||||
|
@ -36,40 +40,53 @@ impl EventReader {
|
|||
) -> Self {
|
||||
let mut position_vector: Vec<i32> = Vec::new();
|
||||
for i in [0, 0] {position_vector.push(i)};
|
||||
let cursor_position_vector_mutex = Arc::new(Mutex::new(position_vector.clone()));
|
||||
let scroll_position_vector_mutex = Arc::new(Mutex::new(position_vector.clone()));
|
||||
let lstick_position = Arc::new(Mutex::new(position_vector.clone()));
|
||||
let rstick_position = Arc::new(Mutex::new(position_vector.clone()));
|
||||
let device_is_connected: Arc<Mutex<bool>> = Arc::new(Mutex::new(true));
|
||||
let virt_dev = Arc::new(Mutex::new(VirtualDevices::new()));
|
||||
let cursor_analog_mode: String = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("CURSOR_STICK").unwrap_or(&"left".to_string()).to_string();
|
||||
let scroll_analog_mode: String = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("SCROLL_STICK").unwrap_or(&"right".to_string()).to_string();
|
||||
let cursor_sensitivity: u64 = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("CURSOR_SENSITIVITY").unwrap_or(&"0".to_string()).parse::<u64>().expect("Invalid cursor sensitivity.");
|
||||
let scroll_sensitivity: u64 = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("SCROLL_SENSITIVITY").unwrap_or(&"0".to_string()).parse::<u64>().expect("Invalid scroll sensitivity.");
|
||||
let has_signed_axis_value: bool = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("SIGNED_AXIS_VALUE").unwrap_or(&"false".to_string()).parse().expect("SIGNED_AXIS_VALUE can only be true or false.");
|
||||
let deadzone: i32 = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("DEADZONE").unwrap_or(&"5".to_string()).parse::<i32>().expect("Invalid value for DEADZONE, please use an integer between 0 and 128.");
|
||||
|
||||
let lstick_function = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("LSTICK").unwrap_or(&"cursor".to_string()).to_string();
|
||||
let lstick_sensitivity: u64 = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("LSTICK_SENSITIVITY").unwrap_or(&"0".to_string()).parse::<u64>().expect("Invalid value for LSTICK_SENSITIVITY, please use an integer value >= 0");
|
||||
let lstick_deadzone: i32 = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("LSTICK_DEADZONE").unwrap_or(&"5".to_string()).parse::<i32>().expect("Invalid value for LSTICK_DEADZONE, please use an integer between 0 and 128.");
|
||||
let lstick = Stick {
|
||||
function: lstick_function,
|
||||
sensitivity: lstick_sensitivity,
|
||||
deadzone: lstick_deadzone,
|
||||
};
|
||||
|
||||
let rstick_function: String = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("RSTICK").unwrap_or(&"scroll".to_string()).to_string();
|
||||
let rstick_sensitivity: u64 = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("RSTICK_SENSITIVITY").unwrap_or(&"0".to_string()).parse::<u64>().expect("Invalid value for RSTICK_SENSITIVITY, please use an integer value >= 0");
|
||||
let rstick_deadzone: i32 = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("RSTICK_DEADZONE").unwrap_or(&"5".to_string()).parse::<i32>().expect("Invalid value for RSTICK_DEADZONE, please use an integer between 0 and 128.");
|
||||
let rstick = Stick {
|
||||
function: rstick_function,
|
||||
sensitivity: rstick_sensitivity,
|
||||
deadzone: rstick_deadzone,
|
||||
};
|
||||
|
||||
let axis_16_bit: bool = config.get(&"default".to_string()).unwrap()
|
||||
.settings.get("16_BIT_AXIS").unwrap_or(&"false".to_string()).parse().expect("16_BIT_AXIS can only be true or false.");
|
||||
|
||||
let settings = Settings {
|
||||
cursor_analog_mode: cursor_analog_mode,
|
||||
scroll_analog_mode: scroll_analog_mode,
|
||||
cursor_sensitivity: cursor_sensitivity,
|
||||
scroll_sensitivity: scroll_sensitivity,
|
||||
has_signed_axis_value: has_signed_axis_value,
|
||||
deadzone: deadzone,
|
||||
lstick,
|
||||
rstick,
|
||||
axis_16_bit,
|
||||
};
|
||||
Self {
|
||||
config: config,
|
||||
stream: stream,
|
||||
virt_dev: virt_dev,
|
||||
cursor_analog_position: cursor_position_vector_mutex,
|
||||
scroll_analog_position: scroll_position_vector_mutex,
|
||||
modifiers: modifiers,
|
||||
device_is_connected: device_is_connected,
|
||||
current_desktop: current_desktop,
|
||||
settings: settings,
|
||||
config,
|
||||
stream,
|
||||
virt_dev,
|
||||
lstick_position,
|
||||
rstick_position,
|
||||
modifiers,
|
||||
device_is_connected,
|
||||
current_desktop,
|
||||
settings,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -102,41 +119,79 @@ impl EventReader {
|
|||
(_, _, AbsoluteAxisType::ABS_HAT0X) => {
|
||||
let event_string: String = match event.value() {
|
||||
-1 => "BTN_DPAD_LEFT".to_string(),
|
||||
0 => "NONE_X".to_string(),
|
||||
0 => "BTN_DPAD_X".to_string(),
|
||||
1 => "BTN_DPAD_RIGHT".to_string(),
|
||||
_ => "NONE_X".to_string(),
|
||||
_ => "BTN_DPAD_X".to_string(),
|
||||
};
|
||||
self.convert_axis_events(event, &event_string, false, false).await;
|
||||
},
|
||||
(_, _, AbsoluteAxisType::ABS_HAT0Y) => {
|
||||
let event_string: String = match event.value() {
|
||||
-1 => "BTN_DPAD_UP".to_string(),
|
||||
0 => "NONE_Y".to_string(),
|
||||
0 => "BTN_DPAD_Y".to_string(),
|
||||
1 => "BTN_DPAD_DOWN".to_string(),
|
||||
_ => "NONE_Y".to_string(),
|
||||
_ => "BTN_DPAD_Y".to_string(),
|
||||
};
|
||||
self.convert_axis_events(event, &event_string, false, false).await;
|
||||
},
|
||||
(EventType::ABSOLUTE, _, AbsoluteAxisType::ABS_X | AbsoluteAxisType::ABS_Y) => {
|
||||
if self.settings.cursor_analog_mode == "left".to_string() {
|
||||
let axis_value = self.get_axis_value(&event).await;
|
||||
let mut cursor_analog_position = self.cursor_analog_position.lock().await;
|
||||
cursor_analog_position[event.code() as usize] = axis_value;
|
||||
} else if self.settings.scroll_analog_mode == "left".to_string() {
|
||||
let axis_value = self.get_axis_value(&event).await;
|
||||
let mut scroll_analog_position = self.scroll_analog_position.lock().await;
|
||||
scroll_analog_position[event.code() as usize] = axis_value;
|
||||
if ["cursor", "scroll"].contains(&self.settings.lstick.function.as_str()) {
|
||||
let axis_value = self.get_axis_value(&event, &self.settings.lstick.deadzone).await;
|
||||
let mut lstick_position = self.lstick_position.lock().await;
|
||||
lstick_position[event.code() as usize] = axis_value;
|
||||
} else if self.settings.lstick.function.as_str() == "bind" {
|
||||
let axis_value = self.get_axis_value(&event, &self.settings.lstick.deadzone).await;
|
||||
let clamped_value = if axis_value < 0 { -1 }
|
||||
else if axis_value > 0 { 1 }
|
||||
else { 0 };
|
||||
let axis = if AbsoluteAxisType(event.code()) == AbsoluteAxisType::ABS_X { "x" }
|
||||
else if AbsoluteAxisType(event.code()) == AbsoluteAxisType::ABS_Y { "y" }
|
||||
else { "none" };
|
||||
let event_string_option: Option<String> = match clamped_value {
|
||||
-1 if axis == "x" => Option::Some("LSTICK_LEFT".to_string()),
|
||||
-1 if axis == "y" => Option::Some("LSTICK_UP".to_string()),
|
||||
0 if axis == "x" => Option::Some("LSTICK_X".to_string()),
|
||||
0 if axis == "y" => Option::Some("LSTICK_Y".to_string()),
|
||||
1 if axis == "x" => Option::Some("LSTICK_RIGHT".to_string()),
|
||||
1 if axis == "y" => Option::Some("LSTICK_DOWN".to_string()),
|
||||
_ => Option::None,
|
||||
};
|
||||
if let Some(event_string) = event_string_option {
|
||||
let clamped_event = InputEvent::new_now(event.event_type(), event.code(), clamped_value);
|
||||
self.convert_axis_events(clamped_event, &event_string, false, false).await;
|
||||
}
|
||||
} else {
|
||||
self.emit_default_event(event).await;
|
||||
}
|
||||
},
|
||||
(EventType::ABSOLUTE, _, AbsoluteAxisType::ABS_RX | AbsoluteAxisType::ABS_RY) => {
|
||||
if self.settings.cursor_analog_mode == "right".to_string() {
|
||||
let axis_value = self.get_axis_value(&event).await;
|
||||
let mut cursor_analog_position = self.cursor_analog_position.lock().await;
|
||||
cursor_analog_position[event.code() as usize -3] = axis_value;
|
||||
} else if self.settings.scroll_analog_mode == "right".to_string() {
|
||||
let axis_value = self.get_axis_value(&event).await;
|
||||
let mut scroll_analog_position = self.scroll_analog_position.lock().await;
|
||||
scroll_analog_position[event.code() as usize -3] = axis_value;
|
||||
if ["cursor", "scroll"].contains(&self.settings.rstick.function.as_str()) {
|
||||
let axis_value = self.get_axis_value(&event, &self.settings.rstick.deadzone).await;
|
||||
let mut rstick_position = self.rstick_position.lock().await;
|
||||
rstick_position[event.code() as usize -3] = axis_value;
|
||||
} else if self.settings.rstick.function.as_str() == "bind" {
|
||||
let axis_value = self.get_axis_value(&event, &self.settings.rstick.deadzone).await;
|
||||
let clamped_value = if axis_value < 0 { -1 }
|
||||
else if axis_value > 0 { 1 }
|
||||
else { 0 };
|
||||
let axis = if AbsoluteAxisType(event.code()) == AbsoluteAxisType::ABS_RX { "x" }
|
||||
else if AbsoluteAxisType(event.code()) == AbsoluteAxisType::ABS_RY { "y" }
|
||||
else { "none" };
|
||||
let event_string_option: Option<String> = match clamped_value {
|
||||
-1 if axis == "x" => Option::Some("RSTICK_LEFT".to_string()),
|
||||
-1 if axis == "y" => Option::Some("RSTICK_UP".to_string()),
|
||||
0 if axis == "x" => Option::Some("RSTICK_X".to_string()),
|
||||
0 if axis == "y" => Option::Some("RSTICK_Y".to_string()),
|
||||
1 if axis == "x" => Option::Some("RSTICK_RIGHT".to_string()),
|
||||
1 if axis == "y" => Option::Some("RSTICK_DOWN".to_string()),
|
||||
_ => Option::None,
|
||||
};
|
||||
if let Some(event_string) = event_string_option {
|
||||
let clamped_event = InputEvent::new_now(event.event_type(), event.code(), clamped_value);
|
||||
self.convert_axis_events(clamped_event, &event_string, false, false).await;
|
||||
}
|
||||
} else {
|
||||
self.emit_default_event(event).await;
|
||||
}
|
||||
},
|
||||
(EventType::ABSOLUTE, _, AbsoluteAxisType::ABS_Z) => {
|
||||
|
@ -189,6 +244,7 @@ impl EventReader {
|
|||
}
|
||||
}
|
||||
if let Some(event_list) = path.bindings.axis.get(event_string) {
|
||||
println!("{:?}", event_list);
|
||||
self.emit_event(event_list, value).await;
|
||||
if send_zero {
|
||||
self.emit_event_without_modifiers(event_list, &modifiers, 0).await;
|
||||
|
@ -250,12 +306,12 @@ impl EventReader {
|
|||
}
|
||||
}
|
||||
|
||||
async fn get_axis_value(&self, event: &InputEvent) -> i32 {
|
||||
let distance_from_center: i32 = match self.settings.has_signed_axis_value {
|
||||
async fn get_axis_value(&self, event: &InputEvent, deadzone: &i32) -> i32 {
|
||||
let distance_from_center: i32 = match self.settings.axis_16_bit {
|
||||
false => (event.value() as i32 - 128) * 200,
|
||||
_ => event.value() as i32
|
||||
};
|
||||
if distance_from_center.abs() <= self.settings.deadzone * 200 {
|
||||
if distance_from_center.abs() <= deadzone * 200 {
|
||||
0
|
||||
} else {
|
||||
(distance_from_center + 2000 - 1) / 2000
|
||||
|
@ -282,19 +338,32 @@ impl EventReader {
|
|||
}
|
||||
|
||||
pub async fn cursor_loop(&self) {
|
||||
if self.settings.cursor_sensitivity != 0 {
|
||||
let (cursor, sensitivity) = if self.settings.lstick.function.as_str() == "cursor" {
|
||||
("left", self.settings.lstick.sensitivity)
|
||||
} else if self.settings.rstick.function.as_str() == "cursor" {
|
||||
("right", self.settings.rstick.sensitivity)
|
||||
} else {
|
||||
("disabled", 0)
|
||||
};
|
||||
if sensitivity != 0 {
|
||||
while *self.device_is_connected.lock().await {
|
||||
{
|
||||
let cursor_analog_position = self.cursor_analog_position.lock().await;
|
||||
if cursor_analog_position[0] != 0 || cursor_analog_position[1] != 0 {
|
||||
let virtual_event_x: InputEvent = InputEvent::new_now(EventType::RELATIVE, 0, cursor_analog_position[0]);
|
||||
let virtual_event_y: InputEvent = InputEvent::new_now(EventType::RELATIVE, 1, cursor_analog_position[1]);
|
||||
let stick_position = if cursor == "left" {
|
||||
self.lstick_position.lock().await
|
||||
} else if cursor == "right" {
|
||||
self.rstick_position.lock().await
|
||||
} else {
|
||||
break
|
||||
};
|
||||
if stick_position[0] != 0 || stick_position[1] != 0 {
|
||||
let virtual_event_x: InputEvent = InputEvent::new_now(EventType::RELATIVE, 0, stick_position[0]);
|
||||
let virtual_event_y: InputEvent = InputEvent::new_now(EventType::RELATIVE, 1, stick_position[1]);
|
||||
let mut virt_dev = self.virt_dev.lock().await;
|
||||
virt_dev.axis.emit(&[virtual_event_x]).unwrap();
|
||||
virt_dev.axis.emit(&[virtual_event_y]).unwrap();
|
||||
}
|
||||
}
|
||||
tokio::time::sleep(std::time::Duration::from_millis(self.settings.cursor_sensitivity)).await;
|
||||
tokio::time::sleep(std::time::Duration::from_millis(sensitivity)).await;
|
||||
}
|
||||
} else {
|
||||
return
|
||||
|
@ -302,19 +371,32 @@ impl EventReader {
|
|||
}
|
||||
|
||||
pub async fn scroll_loop(&self) {
|
||||
if self.settings.scroll_sensitivity != 0 {
|
||||
let (scroll, sensitivity) = if self.settings.lstick.function.as_str() == "scroll" {
|
||||
("left", self.settings.lstick.sensitivity)
|
||||
} else if self.settings.rstick.function.as_str() == "scroll" {
|
||||
("right", self.settings.rstick.sensitivity)
|
||||
} else {
|
||||
("disabled", 0)
|
||||
};
|
||||
if sensitivity != 0 {
|
||||
while *self.device_is_connected.lock().await {
|
||||
{
|
||||
let scroll_analog_position = self.scroll_analog_position.lock().await;
|
||||
if scroll_analog_position[0] != 0 || scroll_analog_position[1] != 0 {
|
||||
let virtual_event_x: InputEvent = InputEvent::new_now(EventType::RELATIVE, 12, scroll_analog_position[0]);
|
||||
let virtual_event_y: InputEvent = InputEvent::new_now(EventType::RELATIVE, 11, scroll_analog_position[1]);
|
||||
let stick_position = if scroll == "left" {
|
||||
self.lstick_position.lock().await
|
||||
} else if scroll == "right" {
|
||||
self.rstick_position.lock().await
|
||||
} else {
|
||||
break
|
||||
};
|
||||
if stick_position[0] != 0 || stick_position[1] != 0 {
|
||||
let virtual_event_x: InputEvent = InputEvent::new_now(EventType::RELATIVE, 12, stick_position[0]);
|
||||
let virtual_event_y: InputEvent = InputEvent::new_now(EventType::RELATIVE, 11, stick_position[1]);
|
||||
let mut virt_dev = self.virt_dev.lock().await;
|
||||
virt_dev.axis.emit(&[virtual_event_x]).unwrap();
|
||||
virt_dev.axis.emit(&[virtual_event_y]).unwrap();
|
||||
}
|
||||
}
|
||||
tokio::time::sleep(std::time::Duration::from_millis(self.settings.scroll_sensitivity)).await;
|
||||
tokio::time::sleep(std::time::Duration::from_millis(sensitivity)).await;
|
||||
}
|
||||
} else {
|
||||
return
|
||||
|
|
Loading…
Add table
Reference in a new issue