diff --git a/src/device.rs b/src/device.rs index 9af5d2c..b63c333 100644 --- a/src/device.rs +++ b/src/device.rs @@ -155,7 +155,7 @@ impl Device { None => Vec::new(), }; - let outputs = Self::flatten( + let outputs = flatten( self.supported_events .iter() .map(|(event_type, kinds)| { @@ -219,8 +219,8 @@ impl Device { } } - fn flatten(vv: Vec>) -> Vec { - vv.into_iter().flatten().collect() + pub fn events(&self) -> &HashMap> { + &self.supported_events } } diff --git a/src/event_code_iters.rs b/src/event_code_iters.rs index 9e1e563..c67cbd2 100644 --- a/src/event_code_iters.rs +++ b/src/event_code_iters.rs @@ -679,3 +679,7 @@ pub fn code_to_string(code: &EventCode) -> String { _ => panic!(), } } + +pub fn flatten(vv: Vec>) -> Vec { + vv.into_iter().flatten().collect() +} diff --git a/src/graph_editor_egui.rs b/src/graph_editor_egui.rs index fd198a4..06aec84 100644 --- a/src/graph_editor_egui.rs +++ b/src/graph_editor_egui.rs @@ -56,7 +56,7 @@ pub fn draw_graph_editor( } node_finder_area.show(ctx, |ui| { // don't allow a nodes to be duplicated - let devs: Vec<&Device> = devices + let missing_devices: Vec<&Device> = devices .iter() .filter(|device| { let mut allow = true; @@ -72,7 +72,29 @@ pub fn draw_graph_editor( }) .collect(); - if let Some(node_device) = node_finder.show(&devs, virtual_device.is_none(), ui) { + if let Some(mut node_device) = + node_finder.show(&missing_devices, virtual_device.is_none(), ui) + { + if let SelectedDevice::Virtual(virt) = &mut node_device { + let existing_devices: Vec<&Device> = devices + .iter() + .filter(|device| { + let mut exists = false; + + for (_node_id, node) in state.graph.nodes.iter() { + if node.op_name == device.name() { + exists = true; + break; + } + } + + exists + }) + .collect(); + + virt.build_ports(&existing_devices); + } + let new_node = state.graph.add_node(node_device.to_descriptor()); state .node_positions diff --git a/src/node_finder.rs b/src/node_finder.rs index fa037c2..e38da52 100644 --- a/src/node_finder.rs +++ b/src/node_finder.rs @@ -58,6 +58,7 @@ impl NodeFinder { // The archetype that will be returned. let mut submitted_device = None; frame.show(ui, |ui| { + ui.set_width(250.0); ui.vertical(|ui| { Frame::default().margin(vec2(10.0, 10.0)).show(ui, |ui| { if allow_virt_dev { diff --git a/src/virtual_device.rs b/src/virtual_device.rs index 9227496..ae23d21 100644 --- a/src/virtual_device.rs +++ b/src/virtual_device.rs @@ -1,8 +1,20 @@ -use crate::{graph_types::NodeDescriptor, id_types::NodeId}; +use std::collections::{HashMap, HashSet}; + +use evdev_rs::enums::{EventCode, EventType}; + +use crate::{ + device::Device, + event_code_iters::{code_to_string, flatten}, + graph_types::{Descriptor, NodeDescriptor}, + id_types::NodeId, +}; pub struct VirtualDevice { name: String, node_id: Option, + + inputs: HashMap>, + outputs: HashMap>, } impl VirtualDevice { @@ -10,6 +22,9 @@ impl VirtualDevice { Self { name: name.to_string(), node_id: None, + + inputs: HashMap::new(), + outputs: HashMap::new(), } } @@ -17,6 +32,62 @@ impl VirtualDevice { self.node_id = Some(node_id); } + pub fn build_ports(&mut self, devices: &[&Device]) { + let mut inputs: HashMap> = HashMap::new(); + let mut outputs: HashMap> = HashMap::new(); + + for device in devices { + for (event_type, new_codes) in device.events() { + match event_type { + EventType::EV_KEY | EventType::EV_REL | EventType::EV_ABS => { + match inputs.get_mut(event_type) { + Some(codes) => { + for code in new_codes { + codes.insert(*code); + } + } + None => { + let mut codes = HashSet::new(); + + for code in new_codes { + codes.insert(*code); + } + + inputs.insert(*event_type, codes); + } + } + } + EventType::EV_FF => match outputs.get_mut(event_type) { + Some(codes) => { + for code in new_codes { + codes.insert(*code); + } + } + None => { + let mut codes = HashSet::new(); + + for code in new_codes { + codes.insert(*code); + } + + outputs.insert(*event_type, codes); + } + }, + + _ => (), + } + } + } + + for (event_type, codes) in inputs { + self.inputs.insert(event_type, codes.into_iter().collect()); + } + + for (event_type, codes) in outputs { + self.outputs.insert(event_type, codes.into_iter().collect()); + } + } + pub fn node_id(&self) -> NodeId { self.node_id.unwrap() } @@ -24,8 +95,28 @@ impl VirtualDevice { pub fn to_descriptor(&self) -> NodeDescriptor { NodeDescriptor { op_name: self.name.clone(), - inputs: Vec::new(), - outputs: Vec::new(), + inputs: flatten( + self.inputs + .iter() + .map(|(_event_type, codes)| { + codes + .iter() + .map(|code| (code_to_string(code), Descriptor::Button)) + .collect::>() + }) + .collect::>>(), + ), + outputs: flatten( + self.outputs + .iter() + .map(|(_event_type, codes)| { + codes + .iter() + .map(|code| (code_to_string(code), Descriptor::Button)) + .collect::>() + }) + .collect::>>(), + ), } } }